]> git.kernelconcepts.de Git - karo-tx-uboot.git/blobdiff - arch/powerpc/cpu/mpc85xx/cpu.c
Merge remote-tracking branch 'u-boot-ti/master'
[karo-tx-uboot.git] / arch / powerpc / cpu / mpc85xx / cpu.c
index 4ef9be1b228e80389f33005c8f5dcc5caf0bf5bf..db232e64f841aac58a7a8d6357aaeb695c6a20a5 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright 2004,2007-2010 Freescale Semiconductor, Inc.
+ * Copyright 2004,2007-2011 Freescale Semiconductor, Inc.
  * (C) Copyright 2002, 2003 Motorola Inc.
  * Xianghua Xiao (X.Xiao@motorola.com)
  *
@@ -33,6 +33,7 @@
 #include <asm/cache.h>
 #include <asm/io.h>
 #include <asm/mmu.h>
+#include <asm/fsl_ifc.h>
 #include <asm/fsl_law.h>
 #include <asm/fsl_lbc.h>
 #include <post.h>
 
 DECLARE_GLOBAL_DATA_PTR;
 
+/*
+ * Default board reset function
+ */
+static void
+__board_reset(void)
+{
+       /* Do nothing */
+}
+void board_reset(void) __attribute__((weak, alias("__board_reset")));
+
 int checkcpu (void)
 {
        sys_info_t sysinfo;
        uint pvr, svr;
-       uint fam;
        uint ver;
        uint major, minor;
        struct cpu_type *cpu;
        char buf1[32], buf2[32];
-#if defined(CONFIG_DDR_CLK_FREQ) || defined(CONFIG_FSL_CORENET)
+#if (defined(CONFIG_DDR_CLK_FREQ) || \
+       defined(CONFIG_FSL_CORENET)) && !defined(CONFIG_SYS_FSL_QORIQ_CHASSIS2)
        volatile ccsr_gur_t *gur = (void *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
 #endif /* CONFIG_FSL_CORENET */
-#ifdef CONFIG_DDR_CLK_FREQ
-       u32 ddr_ratio = ((gur->porpllsr) & MPC85xx_PORPLLSR_DDR_RATIO)
-               >> MPC85xx_PORPLLSR_DDR_RATIO_SHIFT;
-#else
+
+       /*
+        * Cornet platforms use ddr sync bit in RCW to indicate sync vs async
+        * mode. Previous platform use ddr ratio to do the same. This
+        * information is only for display here.
+        */
 #ifdef CONFIG_FSL_CORENET
+#ifdef CONFIG_SYS_FSL_QORIQ_CHASSIS2
+       u32 ddr_sync = 0;       /* only async mode is supported */
+#else
        u32 ddr_sync = ((gur->rcwsr[5]) & FSL_CORENET_RCWSR5_DDR_SYNC)
                >> FSL_CORENET_RCWSR5_DDR_SYNC_SHIFT;
+#endif /* CONFIG_SYS_FSL_QORIQ_CHASSIS2 */
+#else  /* CONFIG_FSL_CORENET */
+#ifdef CONFIG_DDR_CLK_FREQ
+       u32 ddr_ratio = ((gur->porpllsr) & MPC85xx_PORPLLSR_DDR_RATIO)
+               >> MPC85xx_PORPLLSR_DDR_RATIO_SHIFT;
 #else
        u32 ddr_ratio = 0;
-#endif /* CONFIG_FSL_CORENET */
 #endif /* CONFIG_DDR_CLK_FREQ */
-       int i;
+#endif /* CONFIG_FSL_CORENET */
+
+       unsigned int i, core, nr_cores = cpu_numcores();
+       u32 mask = cpu_mask();
 
        svr = get_svr();
        major = SVR_MAJ(svr);
-#ifdef CONFIG_MPC8536
-       major &= 0x7; /* the msb of this nibble is a mfg code */
-#endif
        minor = SVR_MIN(svr);
 
        if (cpu_numcores() > 1) {
@@ -93,42 +113,45 @@ int checkcpu (void)
        printf(", Version: %d.%d, (0x%08x)\n", major, minor, svr);
 
        pvr = get_pvr();
-       fam = PVR_FAM(pvr);
        ver = PVR_VER(pvr);
        major = PVR_MAJ(pvr);
        minor = PVR_MIN(pvr);
 
        printf("Core:  ");
-       if (PVR_FAM(PVR_85xx)) {
-               switch(PVR_MEM(pvr)) {
-               case 0x1:
-               case 0x2:
-                       puts("E500");
-                       break;
-               case 0x3:
-                       puts("E500MC");
-                       break;
-               case 0x4:
-                       puts("E5500");
-                       break;
-               default:
-                       puts("Unknown");
-                       break;
-               }
-       } else {
+       switch(ver) {
+       case PVR_VER_E500_V1:
+       case PVR_VER_E500_V2:
+               puts("E500");
+               break;
+       case PVR_VER_E500MC:
+               puts("E500MC");
+               break;
+       case PVR_VER_E5500:
+               puts("E5500");
+               break;
+       case PVR_VER_E6500:
+               puts("E6500");
+               break;
+       default:
                puts("Unknown");
+               break;
        }
 
        printf(", Version: %d.%d, (0x%08x)\n", major, minor, pvr);
 
+       if (nr_cores > CONFIG_MAX_CPUS) {
+               panic("\nUnexpected number of cores: %d, max is %d\n",
+                       nr_cores, CONFIG_MAX_CPUS);
+       }
+
        get_sys_info(&sysinfo);
 
        puts("Clock Configuration:");
-       for (i = 0; i < cpu_numcores(); i++) {
+       for_each_cpu(i, core, nr_cores, mask) {
                if (!(i & 3))
                        printf ("\n       ");
-               printf("CPU%d:%-4s MHz, ",
-                               i,strmhz(buf1, sysinfo.freqProcessor[i]));
+               printf("CPU%d:%-4s MHz, ", core,
+                       strmhz(buf1, sysinfo.freqProcessor[core]));
        }
        printf("\n       CCB:%-4s MHz,\n", strmhz(buf1, sysinfo.freqSystemBus));
 
@@ -166,12 +189,18 @@ int checkcpu (void)
        }
 #endif
 
+#if defined(CONFIG_FSL_LBC)
        if (sysinfo.freqLocalBus > LCRR_CLKDIV) {
                printf("LBC:%-4s MHz\n", strmhz(buf1, sysinfo.freqLocalBus));
        } else {
                printf("LBC: unknown (LCRR[CLKDIV] = 0x%02lx)\n",
                       sysinfo.freqLocalBus);
        }
+#endif
+
+#if defined(CONFIG_FSL_IFC)
+       printf("IFC:%-4s MHz\n", strmhz(buf1, sysinfo.freqLocalBus));
+#endif
 
 #ifdef CONFIG_CPM2
        printf("CPM:   %s MHz\n", strmhz(buf1, sysinfo.freqSystemBus));
@@ -188,6 +217,10 @@ int checkcpu (void)
        }
 #endif
 
+#ifdef CONFIG_SYS_DPAA_QBMAN
+       printf("       QMAN:  %s MHz\n", strmhz(buf1, sysinfo.freqQMAN));
+#endif
+
 #ifdef CONFIG_SYS_DPAA_PME
        printf("       PME:   %s MHz\n", strmhz(buf1, sysinfo.freqPME));
 #endif
@@ -220,7 +253,12 @@ int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
        mtspr(DBCR0,val);
 #else
        volatile ccsr_gur_t *gur = (void *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
-       out_be32(&gur->rstcr, 0x2);     /* HRESET_REQ */
+
+       /* Attempt board-specific reset */
+       board_reset();
+
+       /* Next try asserting HRESET_REQ */
+       out_be32(&gur->rstcr, 0x2);
        udelay(100);
 #endif
 
@@ -231,13 +269,14 @@ int do_reset (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
 /*
  * Get timebase clock frequency
  */
+#ifndef CONFIG_SYS_FSL_TBCLK_DIV
+#define CONFIG_SYS_FSL_TBCLK_DIV 8
+#endif
 unsigned long get_tbclk (void)
 {
-#ifdef CONFIG_FSL_CORENET
-       return (gd->bus_clk + 8) / 16;
-#else
-       return (gd->bus_clk + 4UL)/8UL;
-#endif
+       unsigned long tbclk_div = CONFIG_SYS_FSL_TBCLK_DIV;
+
+       return (gd->bus_clk + (tbclk_div >> 1)) / tbclk_div;
 }
 
 
@@ -256,10 +295,7 @@ reset_85xx_watchdog(void)
        /*
         * Clear TSR(WIS) bit by writing 1
         */
-       unsigned long val;
-       val = mfspr(SPRN_TSR);
-       val |= TSR_WIS;
-       mtspr(SPRN_TSR, val);
+       mtspr(SPRN_TSR, TSR_WIS);
 }
 #endif /* CONFIG_WATCHDOG */
 
@@ -278,17 +314,34 @@ int cpu_mmc_init(bd_t *bis)
 
 /*
  * Print out the state of various machine registers.
- * Currently prints out LAWs, BR0/OR0, and TLBs
+ * Currently prints out LAWs, BR0/OR0 for LBC, CSPR/CSOR/Timing
+ * parameters for IFC and TLBs
  */
 void mpc85xx_reginfo(void)
 {
        print_tlbcam();
        print_laws();
+#if defined(CONFIG_FSL_LBC)
        print_lbc_regs();
+#endif
+#ifdef CONFIG_FSL_IFC
+       print_ifc_regs();
+#endif
+
 }
 
 /* Common ddr init for non-corenet fsl 85xx platforms */
 #ifndef CONFIG_FSL_CORENET
+#if defined(CONFIG_SYS_RAMBOOT) && !defined(CONFIG_SYS_INIT_L2_ADDR)
+phys_size_t initdram(int board_type)
+{
+#if defined(CONFIG_SPD_EEPROM) || defined(CONFIG_DDR_SPD)
+       return fsl_ddr_sdram_size();
+#else
+       return CONFIG_SYS_SDRAM_SIZE * 1024 * 1024;
+#endif
+}
+#else /* CONFIG_SYS_RAMBOOT */
 phys_size_t initdram(int board_type)
 {
        phys_size_t dram_size = 0;
@@ -315,7 +368,9 @@ phys_size_t initdram(int board_type)
        }
 #endif
 
-#if defined(CONFIG_SPD_EEPROM) || defined(CONFIG_DDR_SPD)
+#if    defined(CONFIG_SPD_EEPROM)      || \
+       defined(CONFIG_DDR_SPD)         || \
+       defined(CONFIG_SYS_DDR_RAW_TIMING)
        dram_size = fsl_ddr_sdram();
 #else
        dram_size = fixed_sdram();
@@ -330,12 +385,15 @@ phys_size_t initdram(int board_type)
        ddr_enable_ecc(dram_size);
 #endif
 
+#if defined(CONFIG_FSL_LBC)
        /* Some boards also have sdram on the lbc */
        lbc_sdram_init();
+#endif
 
-       puts("DDR: ");
+       debug("DDR: ");
        return dram_size;
 }
+#endif /* CONFIG_SYS_RAMBOOT */
 #endif
 
 #if CONFIG_POST & CONFIG_SYS_POST_MEMORY
@@ -348,6 +406,8 @@ void read_tlbcam_entry(int idx, u32 *valid, u32 *tsize, unsigned long *epn,
 unsigned int
        setup_ddr_tlbs_phys(phys_addr_t p_addr, unsigned int memsize_in_meg);
 
+void clear_ddr_tlbs_phys(phys_addr_t p_addr, unsigned int memsize_in_meg);
+
 static void dump_spd_ddr_reg(void)
 {
        int i, j, k, m;
@@ -392,10 +452,20 @@ static void dump_spd_ddr_reg(void)
                case 0:
                        ddr[i] = (void *)CONFIG_SYS_MPC85xx_DDR_ADDR;
                        break;
-#ifdef CONFIG_SYS_MPC85xx_DDR2_ADDR
+#if defined(CONFIG_SYS_MPC85xx_DDR2_ADDR) && (CONFIG_NUM_DDR_CONTROLLERS > 1)
                case 1:
                        ddr[i] = (void *)CONFIG_SYS_MPC85xx_DDR2_ADDR;
                        break;
+#endif
+#if defined(CONFIG_SYS_MPC85xx_DDR3_ADDR) && (CONFIG_NUM_DDR_CONTROLLERS > 2)
+               case 2:
+                       ddr[i] = (void *)CONFIG_SYS_MPC85xx_DDR3_ADDR;
+                       break;
+#endif
+#if defined(CONFIG_SYS_MPC85xx_DDR4_ADDR) && (CONFIG_NUM_DDR_CONTROLLERS > 3)
+               case 3:
+                       ddr[i] = (void *)CONFIG_SYS_MPC85xx_DDR4_ADDR;
+                       break;
 #endif
                default:
                        printf("%s unexpected controller number = %u\n",
@@ -434,19 +504,9 @@ static int reset_tlb(phys_addr_t p_addr, u32 size, phys_addr_t *phys_offset)
        u32 vstart = CONFIG_SYS_DDR_SDRAM_BASE;
        unsigned long epn;
        u32 tsize, valid, ptr;
-       phys_addr_t rpn = 0;
        int ddr_esel;
 
-       ptr = vstart;
-
-       while (ptr < (vstart + size)) {
-               ddr_esel = find_tlb_idx((void *)ptr, 1);
-               if (ddr_esel != -1) {
-                       read_tlbcam_entry(ddr_esel, &valid, &tsize, &epn, &rpn);
-                       disable_tlb(ddr_esel);
-               }
-               ptr += TSIZE_TO_BYTES(tsize);
-       }
+       clear_ddr_tlbs_phys(p_addr, size>>20);
 
        /* Setup new tlb to cover the physical address */
        setup_ddr_tlbs_phys(p_addr, size>>20);