diff options
| author | Jon Loeliger <jdl@freescale.com> | 2008-03-05 18:05:47 -0600 | 
|---|---|---|
| committer | Wolfgang Denk <wd@denx.de> | 2008-03-25 23:00:36 +0100 | 
| commit | 7f1d846e5c5754449c286587d099d85246062772 (patch) | |
| tree | eda55b30fdec51d0d59f5fd8290d087221cb4036 /board/freescale/mpc7448hpc2/tsi108_init.c | |
| parent | b7e24d283e34727c2a6cdfdac2e09a426c579b73 (diff) | |
| download | olio-uboot-2014.01-7f1d846e5c5754449c286587d099d85246062772.tar.xz olio-uboot-2014.01-7f1d846e5c5754449c286587d099d85246062772.zip | |
FSL: Move board/mpc7448hpc2 under board/freescale
Signed-off-by: Jon Loeliger <jdl@freescale.com>
Diffstat (limited to 'board/freescale/mpc7448hpc2/tsi108_init.c')
| -rw-r--r-- | board/freescale/mpc7448hpc2/tsi108_init.c | 665 | 
1 files changed, 665 insertions, 0 deletions
| diff --git a/board/freescale/mpc7448hpc2/tsi108_init.c b/board/freescale/mpc7448hpc2/tsi108_init.c new file mode 100644 index 000000000..30ae17d87 --- /dev/null +++ b/board/freescale/mpc7448hpc2/tsi108_init.c @@ -0,0 +1,665 @@ +/***************************************************************************** + * (C) Copyright 2003;  Tundra Semiconductor Corp. + * + * 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 + *****************************************************************************/ + +/*---------------------------------------------------------------------------- + * FILENAME: tsi108_init.c + * + * Originator: Alex Bounine + * + * DESCRIPTION: + * Initialization code for the Tundra Tsi108 bridge chip + *---------------------------------------------------------------------------*/ + +#include <common.h> +#include <74xx_7xx.h> +#include <config.h> +#include <version.h> +#include <asm/processor.h> +#include <tsi108.h> + +DECLARE_GLOBAL_DATA_PTR; + +extern void mpicInit (int verbose); + +/* + * Configuration Options + */ + +typedef struct { +	ulong upper; +	ulong lower; +} PB2OCN_LUT_ENTRY; + +PB2OCN_LUT_ENTRY pb2ocn_lut1[32] = { +	/* 0 - 7 */ +	{0x00000000, 0x00000201}, /* PBA=0xE000_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE100_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE200_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE300_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE400_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE500_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE600_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE700_0000 -> PCI/X (Byte-Swap) */ + +	/* 8 - 15 */ +	{0x00000000, 0x00000201}, /* PBA=0xE800_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xE900_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xEA00_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xEB00_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xEC00_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xED00_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xEE00_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xEF00_0000 -> PCI/X (Byte-Swap) */ + +	/* 16 - 23 */ +	{0x00000000, 0x00000201}, /* PBA=0xF000_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF100_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF200_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF300_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF400_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF500_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF600_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF700_0000 -> PCI/X (Byte-Swap) */ +	/* 24 - 31 */ +	{0x00000000, 0x00000201}, /* PBA=0xF800_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xF900_0000 -> PCI/X (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xFA00_0000 -> PCI/X  PCI I/O (Byte-Swap) */ +	{0x00000000, 0x00000201}, /* PBA=0xFB00_0000 -> PCI/X  PCI Config (Byte-Swap) */ + +	{0x00000000, 0x02000240}, /* PBA=0xFC00_0000 -> HLP */ +	{0x00000000, 0x01000240}, /* PBA=0xFD00_0000 -> HLP */ +	{0x00000000, 0x03000240}, /* PBA=0xFE00_0000 -> HLP */ +	{0x00000000, 0x00000240}  /* PBA=0xFF00_0000 -> HLP : (Translation Enabled + Byte-Swap)*/ +}; + +#ifdef CFG_CLK_SPREAD +typedef struct { +	ulong ctrl0; +	ulong ctrl1; +} PLL_CTRL_SET; + +/* + * Clock Generator SPLL0 initialization values + * PLL0 configuration table for various PB_CLKO freq. + * Uses pre-calculated values for Fs = 30 kHz, D = 0.5% + * Fout depends on required PB_CLKO. Based on Fref = 33 MHz + */ + +static PLL_CTRL_SET pll0_config[8] = { +	{0x00000000, 0x00000000},	/* 0: bypass */ +	{0x00000000, 0x00000000},	/* 1: reserved */ +	{0x00430044, 0x00000043},	/* 2: CG_PB_CLKO = 183 MHz */ +	{0x005c0044, 0x00000039},	/* 3: CG_PB_CLKO = 100 MHz */ +	{0x005c0044, 0x00000039},	/* 4: CG_PB_CLKO = 133 MHz */ +	{0x004a0044, 0x00000040},	/* 5: CG_PB_CLKO = 167 MHz */ +	{0x005c0044, 0x00000039},	/* 6: CG_PB_CLKO = 200 MHz */ +	{0x004f0044, 0x0000003e}	/* 7: CG_PB_CLKO = 233 MHz */ +}; +#endif	/* CFG_CLK_SPREAD */ + +/* + * Prosessor Bus Clock (in MHz) defined by CG_PB_SELECT + * (based on recommended Tsi108 reference clock 33MHz) + */ +static int pb_clk_sel[8] = { 0, 0, 183, 100, 133, 167, 200, 233 }; + +/* + * get_board_bus_clk () + * + * returns the bus clock in Hz. + */ +unsigned long get_board_bus_clk (void) +{ +	ulong i; + +	/* Detect PB clock freq. */ +	i = in32(CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + CG_PWRUP_STATUS); +	i = (i >> 16) & 0x07;	/* Get PB PLL multiplier */ + +	return pb_clk_sel[i] * 1000000; +} + +/* + * board_early_init_f () + * + * board-specific initialization executed from flash + */ + +int board_early_init_f (void) +{ +	ulong i; + +	gd->mem_clk = 0; +	i = in32 (CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + +			CG_PWRUP_STATUS); +	i = (i >> 20) & 0x07;	/* Get GD PLL multiplier */ +	switch (i) { +	case 0:	/* external clock */ +		printf ("Using external clock\n"); +		break; +	case 1:	/* system clock */ +		gd->mem_clk = gd->bus_clk; +		break; +	case 4:	/* 133 MHz */ +	case 5:	/* 166 MHz */ +	case 6:	/* 200 MHz */ +		gd->mem_clk = pb_clk_sel[i] * 1000000; +		break; +	default: +		printf ("Invalid DDR2 clock setting\n"); +		return -1; +	} +	printf ("BUS: %d MHz\n", get_board_bus_clk() / 1000000); +	printf ("MEM: %d MHz\n", gd->mem_clk / 1000000); +	return 0; +} + +/* + * board_early_init_r() - Tsi108 initialization function executed right after + * relocation. Contains code that cannot be executed from flash. + */ + +int board_early_init_r (void) +{ +	ulong temp, i; +	ulong reg_val; +	volatile ulong *reg_ptr; + +	reg_ptr = +		(ulong *) (CFG_TSI108_CSR_BASE + TSI108_PB_REG_OFFSET + 0x900); + +	for (i = 0; i < 32; i++) { +		*reg_ptr++ = 0x00000201;	/* SWAP ENABLED */ +		*reg_ptr++ = 0x00; +	} + +	__asm__ __volatile__ ("eieio"); +	__asm__ __volatile__ ("sync"); + +	/* Setup PB_OCN_BAR2: size 256B + ENable @ 0x0_80000000 */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PB_REG_OFFSET + PB_OCN_BAR2, +		0x80000001); +	__asm__ __volatile__ ("sync"); + +	/* Make sure that OCN_BAR2 decoder is set (to allow following immediate +	 * read from SDRAM) +	 */ + +	temp = in32(CFG_TSI108_CSR_BASE + TSI108_PB_REG_OFFSET + PB_OCN_BAR2); +	__asm__ __volatile__ ("sync"); + +	/* +	 * Remap PB_OCN_BAR1 to accomodate PCI-bus aperture and EPROM into the +	 * processor bus address space. Immediately after reset LUT and address +	 * translation are disabled for this BAR. Now we have to initialize LUT +	 * and switch from the BOOT mode to the normal operation mode. +	 * +	 * The aperture defined by PB_OCN_BAR1 startes at address 0xE0000000 +	 * and covers 512MB of address space. To allow larger aperture we also +	 * have to relocate register window of Tsi108 +	 * +	 * Initialize LUT (32-entries) prior switching PB_OCN_BAR1 from BOOT +	 * mode. +	 * +	 * initialize pointer to LUT associated with PB_OCN_BAR1 +	 */ +	reg_ptr = +		(ulong *) (CFG_TSI108_CSR_BASE + TSI108_PB_REG_OFFSET + 0x800); + +	for (i = 0; i < 32; i++) { +		*reg_ptr++ = pb2ocn_lut1[i].lower; +		*reg_ptr++ = pb2ocn_lut1[i].upper; +	} + +	__asm__ __volatile__ ("sync"); + +	/* Base addresses for CS0, CS1, CS2, CS3 */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B0_ADDR, +		0x00000000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B1_ADDR, +		0x00100000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B2_ADDR, +		0x00200000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B3_ADDR, +		0x00300000); +	__asm__ __volatile__ ("sync"); + +	/* Masks for HLP banks */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B0_MASK, +		0xFFF00000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B1_MASK, +		0xFFF00000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B2_MASK, +		0xFFF00000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B3_MASK, +		0xFFF00000); +	__asm__ __volatile__ ("sync"); + +	/* Set CTRL0 values for banks */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B0_CTRL0, +		0x7FFC44C2); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B1_CTRL0, +		0x7FFC44C0); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B2_CTRL0, +		0x7FFC44C0); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B3_CTRL0, +		0x7FFC44C2); +	__asm__ __volatile__ ("sync"); + +	/* Set banks to latched mode, enabled, and other default settings */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B0_CTRL1, +		0x7C0F2000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B1_CTRL1, +		0x7C0F2000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B2_CTRL1, +		0x7C0F2000); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_HLP_REG_OFFSET + HLP_B3_CTRL1, +		0x7C0F2000); +	__asm__ __volatile__ ("sync"); + +	/* +	 * Set new value for PB_OCN_BAR1: switch from BOOT to LUT mode. +	 * value for PB_OCN_BAR1: (BA-0xE000_0000 + size 512MB + ENable) +	 */ +	out32 (CFG_TSI108_CSR_BASE + TSI108_PB_REG_OFFSET + PB_OCN_BAR1, +		0xE0000011); +	__asm__ __volatile__ ("sync"); + +	/* Make sure that OCN_BAR2 decoder is set (to allow following +	 * immediate read from SDRAM) +	 */ + +	temp = in32(CFG_TSI108_CSR_BASE + TSI108_PB_REG_OFFSET + PB_OCN_BAR1); +	__asm__ __volatile__ ("sync"); + +	/* +	 * SRI: At this point we have enabled the HLP banks. That means we can +	 * now read from the NVRAM and initialize the environment variables. +	 * We will over-ride the env_init called in board_init_f +	 * This is really a work-around because, the HLP bank 1 +	 * where NVRAM resides is not visible during board_init_f +	 * (lib_ppc/board.c) +	 * Alternatively, we could use the I2C EEPROM at start-up to configure +	 * and enable all HLP banks and not just HLP 0 as is being done for +	 * Taiga Rev. 2. +	 */ + +	env_init (); + +#ifndef DISABLE_PBM + +	/* +	 * For IBM processors we have to set Address-Only commands generated +	 * by PBM that are different from ones set after reset. +	 */ + +	temp = get_cpu_type (); + +	if ((CPU_750FX == temp) || (CPU_750GX == temp)) +		out32 (CFG_TSI108_CSR_BASE + TSI108_PB_REG_OFFSET + PB_MCMD, +			0x00009955); +#endif	/* DISABLE_PBM */ + +#ifdef CONFIG_PCI +	/* +	 * Initialize PCI/X block +	 */ + +	/* Map PCI/X Configuration Space (16MB @ 0x0_FE000000) */ +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + +		PCI_PFAB_BAR0_UPPER, 0); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_PFAB_BAR0, +		0xFB000001); +	__asm__ __volatile__ ("sync"); + +	/* Set Bus Number for the attached PCI/X bus (we will use 0 for NB) */ + +	temp =	in32(CFG_TSI108_CSR_BASE + +		TSI108_PCI_REG_OFFSET + PCI_PCIX_STAT); + +	temp &= ~0xFF00;	/* Clear the BUS_NUM field */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_PCIX_STAT, +		temp); + +	/* Map PCI/X IO Space (64KB @ 0x0_FD000000) takes one 16MB LUT entry */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_PFAB_IO_UPPER, +		0); +	__asm__ __volatile__ ("sync"); + +	/* This register is on the PCI side to interpret the address it receives +	 * and maps it as a IO address. +	 */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_PFAB_IO, +		0xFA000001); +	__asm__ __volatile__ ("sync"); + +	/* +	 * Map PCI/X Memory Space +	 * +	 * Transactions directed from OCM to PCI Memory Space are directed +	 * from PB to PCI +	 * unchanged (as defined by PB_OCN_BAR1,2 and LUT settings). +	 * If address remapping is required the corresponding PCI_PFAB_MEM32 +	 * and PCI_PFAB_PFMx register groups have to be configured. +	 * +	 * Map the path from the PCI/X bus into the system memory +	 * +	 * The memory mapped window assotiated with PCI P2O_BAR2 provides +	 * access to the system memory without address remapping. +	 * All system memory is opened for accesses initiated by PCI/X bus +	 * masters. +	 * +	 * Initialize LUT associated with PCI P2O_BAR2 +	 * +	 * set pointer to LUT associated with PCI P2O_BAR2 +	 */ + +	reg_ptr = +		(ulong *) (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + 0x500); + +#ifdef DISABLE_PBM + +	/* In case when PBM is disabled (no HW supported cache snoopng on PB) +	 * P2O_BAR2 is directly mapped into the system memory without address +	 * translation. +	 */ + +	reg_val = 0x00000004;	/* SDRAM port + NO Addr_Translation */ + +	for (i = 0; i < 32; i++) { +		*reg_ptr++ = reg_val;	/* P2O_BAR2_LUTx */ +		*reg_ptr++ = 0;		/* P2O_BAR2_LUT_UPPERx */ +	} + +	/* value for PCI BAR2 (size = 512MB, Enabled, No Addr. Translation) */ +	reg_val = 0x00007500; +#else + +	reg_val = 0x00000002;	/* Destination port = PBM */ + +	for (i = 0; i < 32; i++) { +		*reg_ptr++ = reg_val;	/* P2O_BAR2_LUTx */ +/* P2O_BAR2_LUT_UPPERx : Set data swapping mode for PBM (byte swapping) */ +		*reg_ptr++ = 0x40000000; +/* offset = 16MB, address translation is enabled to allow byte swapping */ +		reg_val += 0x01000000; +	} + +/* value for PCI BAR2 (size = 512MB, Enabled, Address Translation Enabled) */ +	reg_val = 0x00007100; +#endif + +	__asm__ __volatile__ ("eieio"); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_PAGE_SIZES, +		reg_val); +	__asm__ __volatile__ ("sync"); + +	/* Set 64-bit PCI bus address for system memory +	 * ( 0 is the best choice for easy mapping) +	 */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_BAR2, +		0x00000000); +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_BAR2_UPPER, +		0x00000000); +	__asm__ __volatile__ ("sync"); + +#ifndef DISABLE_PBM +	/* +	 *  The memory mapped window assotiated with PCI P2O_BAR3 provides +	 *  access to the system memory using SDRAM OCN port and address +	 *  translation. This is alternative way to access SDRAM from PCI +	 *  required for Tsi108 emulation testing. +	 *  All system memory is opened for accesses initiated by +	 *  PCI/X bus masters. +	 * +	 *  Initialize LUT associated with PCI P2O_BAR3 +	 * +	 *  set pointer to LUT associated with PCI P2O_BAR3 +	 */ +	reg_ptr = +		(ulong *) (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + 0x600); + +	reg_val = 0x00000004;	/* Destination port = SDC */ + +	for (i = 0; i < 32; i++) { +		*reg_ptr++ = reg_val;	/* P2O_BAR3_LUTx */ + +/* P2O_BAR3_LUT_UPPERx : Set data swapping mode for PBM (byte swapping) */ +		*reg_ptr++ = 0; + +/* offset = 16MB, address translation is enabled to allow byte swapping */ +		reg_val += 0x01000000; +	} + +	__asm__ __volatile__ ("eieio"); +	__asm__ __volatile__ ("sync"); + +	/* Configure PCI P2O_BAR3 (size = 512MB, Enabled) */ + +	reg_val = +		in32(CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + +		 PCI_P2O_PAGE_SIZES); +	reg_val &= ~0x00FF; +	reg_val |= 0x0071; +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_PAGE_SIZES, +		reg_val); +	__asm__ __volatile__ ("sync"); + +	/* Set 64-bit base PCI bus address for window (0x20000000) */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_BAR3_UPPER, +		0x00000000); +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_BAR3, +		0x20000000); +	__asm__ __volatile__ ("sync"); + +#endif	/* !DISABLE_PBM */ + +#ifdef ENABLE_PCI_CSR_BAR +	/* open if required access to Tsi108 CSRs from the PCI/X bus */ +	/* enable BAR0 on the PCI/X bus */ +	reg_val = in32(CFG_TSI108_CSR_BASE + +		TSI108_PCI_REG_OFFSET + PCI_MISC_CSR); +	reg_val |= 0x02; +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_MISC_CSR, +		reg_val); +	__asm__ __volatile__ ("sync"); + +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_BAR0_UPPER, +		0x00000000); +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_P2O_BAR0, +		CFG_TSI108_CSR_BASE); +	__asm__ __volatile__ ("sync"); + +#endif + +	/* +	 * Finally enable PCI/X Bus Master and Memory Space access +	 */ + +	reg_val = in32(CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_CSR); +	reg_val |= 0x06; +	out32 (CFG_TSI108_CSR_BASE + TSI108_PCI_REG_OFFSET + PCI_CSR, reg_val); +	__asm__ __volatile__ ("sync"); + +#endif	/* CONFIG_PCI */ + +	/* +	 * Initialize MPIC outputs (interrupt pins): +	 * Interrupt routing on the Grendel Emul. Board: +	 * PB_INT[0] -> INT (CPU0) +	 * PB_INT[1] -> INT (CPU1) +	 * PB_INT[2] -> MCP (CPU0) +	 * PB_INT[3] -> MCP (CPU1) +	 * Set interrupt controller outputs as Level_Sensitive/Active_Low +	 */ +	out32 (CFG_TSI108_CSR_BASE + TSI108_MPIC_REG_OFFSET + MPIC_CSR(0), 0x02); +	out32 (CFG_TSI108_CSR_BASE + TSI108_MPIC_REG_OFFSET + MPIC_CSR(1), 0x02); +	out32 (CFG_TSI108_CSR_BASE + TSI108_MPIC_REG_OFFSET + MPIC_CSR(2), 0x02); +	out32 (CFG_TSI108_CSR_BASE + TSI108_MPIC_REG_OFFSET + MPIC_CSR(3), 0x02); +	__asm__ __volatile__ ("sync"); + +	/* +	 * Ensure that Machine Check exception is enabled +	 * We need it to support PCI Bus probing (configuration reads) +	 */ + +	reg_val = mfmsr (); +	mtmsr(reg_val | MSR_ME); + +	return 0; +} + +/* + * Needed to print out L2 cache info + * used in the misc_init_r function + */ + +unsigned long get_l2cr (void) +{ +	unsigned long l2controlreg; +	asm volatile ("mfspr %0, 1017":"=r" (l2controlreg):); +	return l2controlreg; +} + +/* + * misc_init_r() + * + * various things to do after relocation + * + */ + +int misc_init_r (void) +{ +#ifdef CFG_CLK_SPREAD	/* Initialize Spread-Spectrum Clock generation */ +	ulong i; + +	/* Ensure that Spread-Spectrum is disabled */ +	out32 (CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + CG_PLL0_CTRL0, 0); +	out32 (CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + CG_PLL1_CTRL0, 0); + +	/* Initialize PLL1: CG_PCI_CLK , internal OCN_CLK +	 * Uses pre-calculated value for Fout = 800 MHz, Fs = 30 kHz, D = 0.5% +	 */ + +	out32 (CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + CG_PLL1_CTRL0, +		0x002e0044);	/* D = 0.25% */ +	out32 (CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + CG_PLL1_CTRL1, +		0x00000039);	/* BWADJ */ + +	/* Initialize PLL0: CG_PB_CLKO  */ +	/* Detect PB clock freq. */ +	i = in32(CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + CG_PWRUP_STATUS); +	i = (i >> 16) & 0x07;	/* Get PB PLL multiplier */ + +	out32 (CFG_TSI108_CSR_BASE + +		TSI108_CLK_REG_OFFSET + CG_PLL0_CTRL0, pll0_config[i].ctrl0); +	out32 (CFG_TSI108_CSR_BASE + +		TSI108_CLK_REG_OFFSET + CG_PLL0_CTRL1, pll0_config[i].ctrl1); + +	/* Wait and set SSEN for both PLL0 and 1 */ +	udelay (1000); +	out32 (CFG_TSI108_CSR_BASE + TSI108_CLK_REG_OFFSET + CG_PLL1_CTRL0, +		0x802e0044);	/* D=0.25% */ +	out32 (CFG_TSI108_CSR_BASE + +		TSI108_CLK_REG_OFFSET + CG_PLL0_CTRL0, +	 	0x80000000 | pll0_config[i].ctrl0); +#endif	/* CFG_CLK_SPREAD */ + +#ifdef CFG_L2 +	l2cache_enable (); +#endif +	printf ("BUS:   %d MHz\n", gd->bus_clk / 1000000); +	printf ("MEM:   %d MHz\n", gd->mem_clk / 1000000); + +	/* +	 * All the information needed to print the cache details is avaiblable +	 * at this point i.e. above call to l2cache_enable is the very last +	 * thing done with regards to enabling diabling the cache. +	 * So this seems like a good place to print all this information +	 */ + +	printf ("CACHE: "); +	switch (get_cpu_type()) { +	case CPU_7447A: +		printf ("L1 Instruction cache - 32KB 8-way"); +		(get_hid0 () & (1 << 15)) ? printf (" ENABLED\n") : +			printf (" DISABLED\n"); +		printf ("L1 Data cache - 32KB 8-way"); +		(get_hid0 () & (1 << 14)) ? printf (" ENABLED\n") : +			printf (" DISABLED\n"); +		printf ("Unified L2 cache - 512KB 8-way"); +		(get_l2cr () & (1 << 31)) ? printf (" ENABLED\n") : +			printf (" DISABLED\n"); +		printf ("\n"); +		break; + +	case CPU_7448: +		printf ("L1 Instruction cache - 32KB 8-way"); +		(get_hid0 () & (1 << 15)) ? printf (" ENABLED\n") : +			printf (" DISABLED\n"); +		printf ("L1 Data cache - 32KB 8-way"); +		(get_hid0 () & (1 << 14)) ? printf (" ENABLED\n") : +			printf (" DISABLED\n"); +		printf ("Unified L2 cache - 1MB 8-way"); +		(get_l2cr () & (1 << 31)) ? printf (" ENABLED\n") : +			printf (" DISABLED\n"); +		break; +	default: +		break; +	} +	return 0; +} |