General code modification for mpc7448hpc2 board support.
1. Add 7447A and 7448 processor support.
2. Add the following flags.

CFG_CONFIG_BUS_CLK : If the 74xx bus frequency can be configured dynamically
(such as by switch on board), this flag should be set.

CFG_EXCEPTION_AFTER_RELOCATE: If an exception occurs after the u-boot
relocates to RAM, this flag should be set.

CFG_SERIAL_HANG_IN_EXCEPTION: If the print out function will cause the
system hang in exception, this flag should be set.

There is a design issue for tsi108/109 pci configure  read. When pci scan
the slots, if there is no pci card, the tsi108/9 will cause a machine
check exception for mpc7448 processor.

Signed-off-by: Alexandre Bounine <alexandreb@tundra.com>
Signed-off-by: Roy Zang <tie-fei.zang@freescale.com>
diff --git a/cpu/74xx_7xx/cpu.c b/cpu/74xx_7xx/cpu.c
index ca45e17..c3aadca 100644
--- a/cpu/74xx_7xx/cpu.c
+++ b/cpu/74xx_7xx/cpu.c
@@ -44,6 +44,10 @@
 #include <74xx_7xx.h>
 #include <asm/cache.h>
 
+#if defined(CONFIG_OF_FLAT_TREE)
+#include <ft_build.h>
+#endif
+
 #ifdef CONFIG_AMIGAONEG3SE
 #include "../board/MAI/AmigaOneG3SE/via686.h"
 #include "../board/MAI/AmigaOneG3SE/memio.h"
@@ -101,6 +105,14 @@
 		type = CPU_7457;
 		break;
 
+	case 0x8003:
+		type = CPU_7447A;
+		break;
+		
+	case 0x8004:
+		type = CPU_7448;
+		break;
+		
 	default:
 		break;
 	}
@@ -164,6 +176,14 @@
 		str = "MPC7457";
 		break;
 
+	case CPU_7447A:
+		str = "MPC7447A";
+		break;
+
+	case CPU_7448:
+		str = "MPC7448";
+		break;
+
 	default:
 		printf("Unknown CPU -- PVR: 0x%08x\n", pvr);
 		return -1;
@@ -256,20 +276,19 @@
 /*
  * For the 7400 the TB clock runs at 1/4 the cpu bus speed.
  */
-#ifdef CONFIG_AMIGAONEG3SE
+#if defined(CONFIG_AMIGAONEG3SE) || defined(CFG_CONFIG_BUS_CLK)
 unsigned long get_tbclk(void)
 {
 	return (gd->bus_clk / 4);
 }
-#else	/* ! CONFIG_AMIGAONEG3SE */
+#else	/* ! CONFIG_AMIGAONEG3SE and !CFG_CONFIG_BUS_CLK*/
 
 unsigned long get_tbclk (void)
 {
 	return CFG_BUS_HZ / 4;
 }
-#endif	/* CONFIG_AMIGAONEG3SE */
+#endif	/* CONFIG_AMIGAONEG3SE or CFG_CONFIG_BUS_CLK*/
 /* ------------------------------------------------------------------------- */
-
 #if defined(CONFIG_WATCHDOG)
 #if !defined(CONFIG_PCIPPC2) && !defined(CONFIG_BAB7xx)
 void
@@ -281,3 +300,30 @@
 #endif	/* CONFIG_WATCHDOG */
 
 /* ------------------------------------------------------------------------- */
+
+#ifdef CONFIG_OF_FLAT_TREE
+void
+ft_cpu_setup(void *blob, bd_t *bd)
+{
+	u32 *p;
+	ulong clock;
+	int len;
+		
+	clock = bd->bi_busfreq;
+	
+	p = ft_get_prop(blob, "/cpus/" OF_CPU "/bus-frequency", &len);
+	if (p != NULL)
+		*p = cpu_to_be32(clock);
+
+#if defined(CONFIG_TSI108_ETH)
+	p = ft_get_prop(blob, "/" OF_TSI "/ethernet@6200/address", &len);
+		memcpy(p, bd->bi_enetaddr, 6);
+#endif
+ 
+#if defined(CONFIG_HAS_ETH1)
+	p = ft_get_prop(blob, "/" OF_TSI "/ethernet@6600/address", &len);
+		memcpy(p, bd->bi_enet1addr, 6);
+#endif
+}
+#endif
+/* ------------------------------------------------------------------------- */
diff --git a/cpu/74xx_7xx/cpu_init.c b/cpu/74xx_7xx/cpu_init.c
index 93f180f..1dd1b2c 100644
--- a/cpu/74xx_7xx/cpu_init.c
+++ b/cpu/74xx_7xx/cpu_init.c
@@ -43,6 +43,8 @@
 	case CPU_7450:
 	case CPU_7455:
 	case CPU_7457:
+	case CPU_7447A:
+	case CPU_7448:
 		/* enable the timebase bit in HID0 */
 		set_hid0(get_hid0() | 0x4000000);
 		break;
diff --git a/cpu/74xx_7xx/speed.c b/cpu/74xx_7xx/speed.c
index 2dc5107..d520794 100644
--- a/cpu/74xx_7xx/speed.c
+++ b/cpu/74xx_7xx/speed.c
@@ -31,6 +31,8 @@
 
 DECLARE_GLOBAL_DATA_PTR;
 
+extern unsigned long get_board_bus_clk(void);
+
 static const int hid1_multipliers_x_10[] = {
 	25,	/* 0000 - 2.5x */
 	75,	/* 0001 - 7.5x */
@@ -50,6 +52,41 @@
 	0	/* 1111 - off */
 };
 
+static const int hid1_7447A_multipliers_x_10[] = {
+	115,    /* 00000 - 11.5x  */
+	170,    /* 00001 - 17x    */
+	75,     /* 00010 -  7.5x  */
+	150,    /* 00011 - 15x    */
+	70,     /* 00100 -  7x    */
+	180,    /* 00101 - 18x    */
+	10,     /* 00110 - bypass */
+	200,    /* 00111 - 20x    */
+	20,     /* 01000 -  2x    */
+	210,    /* 01001 - 21x    */
+	65,     /* 01010 -  6.5x  */
+	130,    /* 01011 - 13x    */
+	85,     /* 01100 -  8.5x  */
+	240,    /* 01101 - 13x    */
+	95,     /* 01110 -  9.5x  */
+	90,     /* 01111 -  9x    */
+	30,     /* 10000 -  3x    */
+	105,    /* 10001 - 10.5x  */
+	55,     /* 10010 -  5.5x  */
+	110,    /* 10011 - 11x    */
+	40,     /* 10100 -  4x    */
+	100,    /* 10101 - 10x    */
+	50,     /* 10110 -  5x    */
+	120,    /* 10111 - 12x    */
+	80,     /* 11000 -  8x    */
+	140,    /* 11001 - 14x    */
+	60,     /* 11010 -  6x    */
+	160,    /* 11011 - 16x    */
+	135,    /* 11100 - 13.5x  */
+	280,    /* 11101 - 28x    */
+	0,      /* 11110 - off    */
+	125     /* 11111 - 12.5x  */
+};
+
 static const int hid1_fx_multipliers_x_10[] = {
 	00,	/* 0000 - off */
 	00,	/* 0001 - off */
@@ -89,8 +126,19 @@
 {
 	ulong clock = 0;
 
+#ifdef CFG_CONFIG_BUS_CLK
+	gd->bus_clk = get_board_bus_clk();
+#else
+	gd->bus_clk = CFG_BUS_CLK;
+#endif
+
 	/* calculate the clock frequency based upon the CPU type */
 	switch (get_cpu_type()) {
+	case CPU_7447A:
+	case CPU_7448:
+		clock = (gd->bus_clk / 10) * hid1_7447A_multipliers_x_10[(get_hid1 () >> 12) & 0x1F];
+		break;
+		
 	case CPU_7455:
 	case CPU_7457:
 		/*
@@ -98,12 +146,12 @@
 		 * Make sure division is done before multiplication to prevent 32-bit
 		 * arithmetic overflows which will cause a negative number
 		 */
-		clock = (CFG_BUS_CLK / 10) * hid1_multipliers_x_10[(get_hid1 () >> 13) & 0xF];
+		clock = (gd->bus_clk / 10) * hid1_multipliers_x_10[(get_hid1 () >> 13) & 0xF];
 		break;
 
 	case CPU_750GX:
 	case CPU_750FX:
-		clock = CFG_BUS_CLK * hid1_fx_multipliers_x_10[get_hid1 () >> 27] / 10;
+		clock = gd->bus_clk * hid1_fx_multipliers_x_10[get_hid1 () >> 27] / 10;
 		break;
 
 	case CPU_7450:
@@ -120,7 +168,7 @@
 		 * Make sure division is done before multiplication to prevent 32-bit
 		 * arithmetic overflows which will cause a negative number
 		 */
-		clock = (CFG_BUS_CLK / 10) * hid1_multipliers_x_10[get_hid1 () >> 28];
+		clock = (gd->bus_clk / 10) * hid1_multipliers_x_10[get_hid1 () >> 28];
 		break;
 
 	case CPU_UNKNOWN:
@@ -130,7 +178,6 @@
 	}
 
 	gd->cpu_clk = clock;
-	gd->bus_clk = CFG_BUS_CLK;
 
 	return (0);
 }