]> git.sur5r.net Git - u-boot/blobdiff - cpu/ppc4xx/4xx_ibm_ddr2_autocalib.c
Move architecture-specific includes to arch/$ARCH/include/asm
[u-boot] / cpu / ppc4xx / 4xx_ibm_ddr2_autocalib.c
index 83b9883a7726efa896300848fb4db4699f51b2dd..0283c91d84109a3533d8aa8a40a23201dea2f21d 100644 (file)
@@ -42,6 +42,8 @@
 #include <asm/io.h>
 #include <asm/processor.h>
 
+#include "ecc.h"
+
 #if defined(CONFIG_PPC4xx_DDR_AUTOCALIBRATION)
 
 /*
 #define MAXBXCF                        4
 #define SDRAM_RXBAS_SHIFT_1M   20
 
-#if defined(CFG_DECREMENT_PATTERNS)
+#if defined(CONFIG_SYS_DECREMENT_PATTERNS)
 #define NUMMEMTESTS            24
 #else
 #define NUMMEMTESTS            8
-#endif /* CFG_DECREMENT_PATTERNS */
+#endif /* CONFIG_SYS_DECREMENT_PATTERNS */
 #define NUMLOOPS               1       /* configure as you deem approporiate */
 #define NUMMEMWORDS            16
 
+#define SDRAM_RDCC_RDSS_VAL(n) SDRAM_RDCC_RDSS_DECODE(ddr_rdss_opt(n))
+
 /* Private Structure Definitions */
 
 struct autocal_regs {
@@ -147,6 +151,13 @@ ulong __ddr_scan_option(ulong default_val)
 }
 ulong ddr_scan_option(ulong) __attribute__((weak, alias("__ddr_scan_option")));
 
+u32 __ddr_rdss_opt(u32 default_val)
+{
+       return default_val;
+}
+u32 ddr_rdss_opt(ulong) __attribute__((weak, alias("__ddr_rdss_opt")));
+
+
 static u32 *get_membase(int bxcr_num)
 {
        ulong bxcf;
@@ -168,12 +179,29 @@ static u32 *get_membase(int bxcr_num)
 
 static inline void ecc_clear_status_reg(void)
 {
-       mtsdram(SDRAM_ECCCR, 0xffffffff);
+       mtsdram(SDRAM_ECCES, 0xffffffff);
 #if defined(SDRAM_R0BAS)
        mtdcr(SDRAM_ERRSTATLL, 0xffffffff);
 #endif
 }
 
+/*
+ * Reset and relock memory DLL after SDRAM_CLKTR change
+ */
+static inline void relock_memory_DLL(void)
+{
+       u32 reg;
+
+       mtsdram(SDRAM_MCOPT2, SDRAM_MCOPT2_IPTR_EXECUTE);
+
+       do {
+               mfsdram(SDRAM_MCSTAT, reg);
+       } while (!(reg & SDRAM_MCSTAT_MIC_COMP));
+
+       mfsdram(SDRAM_MCOPT2, reg);
+       mtsdram(SDRAM_MCOPT2, reg | SDRAM_MCOPT2_DCEN_ENABLE);
+}
+
 static int ecc_check_status_reg(void)
 {
        u32 ecc_status;
@@ -184,7 +212,7 @@ static int ecc_check_status_reg(void)
         * ecc error, then don't count
         * this as a passing value
         */
-       mfsdram(SDRAM_ECCCR, ecc_status);
+       mfsdram(SDRAM_ECCES, ecc_status);
        if (ecc_status != 0x00000000) {
                /* clear on error */
                ecc_clear_status_reg();
@@ -237,7 +265,7 @@ static int short_mem_test(u32 *base_address)
                 0x55AA55AA, 0x55AA55AA, 0xAA55AA55, 0xAA55AA55,
                 0x55AA55AA, 0x55AA55AA, 0xAA55AA55, 0xAA55AA55},
 
-#if defined(CFG_DECREMENT_PATTERNS)
+#if defined(CONFIG_SYS_DECREMENT_PATTERNS)
        /* 8 */ {0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
                 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
                 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
@@ -302,7 +330,7 @@ static int short_mem_test(u32 *base_address)
                 0xfff0fff0, 0xfff0fff0, 0xfff0fff0, 0xfff0fff0,
                 0xfff0fff0, 0xfff0fff0, 0xfff0fff0, 0xfff0fff0,
                 0xfff0fff0, 0xfff0fffe, 0xfff0fff0, 0xfff0fff0},
-#endif /* CFG_DECREMENT_PATTERNS */
+#endif /* CONFIG_SYS_DECREMENT_PATTERNS */
                                                                 };
 
        mfsdram(SDRAM_MCOPT1, ecc_mode);
@@ -324,6 +352,7 @@ static int short_mem_test(u32 *base_address)
                        ppcDcbf((ulong)&(base_address[j]));
                }
                sync();
+               iobarrier_rw();
                for (l = 0; l < NUMLOOPS; l++) {
                        for (j = 0; j < NUMMEMWORDS; j++) {
                                if (base_address[j] != test[i][j]) {
@@ -338,6 +367,7 @@ static int short_mem_test(u32 *base_address)
                                ppcDcbf((u32)&(base_address[j]));
                        } /* for (j = 0; j < NUMMEMWORDS; j++) */
                        sync();
+                       iobarrier_rw();
                } /* for (l=0; l<NUMLOOPS; l++) */
        }
 
@@ -430,7 +460,8 @@ static u32 DQS_calibration_methodA(struct ddrautocal *cal)
         * Program RDCC register
         * Read sample cycle auto-update enable
         */
-       mtsdram(SDRAM_RDCC, SDRAM_RDCC_RDSS_T1 | SDRAM_RDCC_RSAE_ENABLE);
+       mtsdram(SDRAM_RDCC,
+               ddr_rdss_opt(SDRAM_RDCC_RDSS_T2) | SDRAM_RDCC_RSAE_ENABLE);
 
 #ifdef DEBUG
        mfsdram(SDRAM_RDCC, temp);
@@ -616,7 +647,8 @@ static u32 program_DQS_calibration_methodB(struct ddrautocal *ddrcal)
         * Program RDCC register
         * Read sample cycle auto-update enable
         */
-       mtsdram(SDRAM_RDCC, SDRAM_RDCC_RDSS_T2 | SDRAM_RDCC_RSAE_ENABLE);
+       mtsdram(SDRAM_RDCC,
+               ddr_rdss_opt(SDRAM_RDCC_RDSS_T2) | SDRAM_RDCC_RSAE_ENABLE);
 
 #ifdef DEBUG
        mfsdram(SDRAM_RDCC, temp);
@@ -981,6 +1013,8 @@ u32 DQS_autocalibration(void)
 
                mtsdram(SDRAM_CLKTR, clkp << 30);
 
+               relock_memory_DLL();
+
                putc('\b');
                putc(slash[loopi++ % 8]);
 
@@ -1072,32 +1106,36 @@ u32 DQS_autocalibration(void)
                 * if no passing window was found, or is the
                 * size of the RFFD passing window.
                 */
-               if (result != 0) {
-                       tcal.autocal.flags = 1;
-                       debug("*** (%d)(%d) result passed window size: 0x%08x, "
-                             "rqfd = 0x%08x, rffd = 0x%08x, rdcc = 0x%08x\n",
-                               wdtr, clkp, result, ddrcal.rqfd,
-                               ddrcal.rffd, ddrcal.rdcc);
-                       /*
-                        * Save the SDRAM_WRDTR and SDRAM_CLKTR
-                        * settings for the largest returned
-                        * RFFD passing window size.
-                        */
-                       if (result > best_result) {
+               /*
+                * want the lowest Read Sample Cycle Select
+                */
+               val = SDRAM_RDCC_RDSS_DECODE(val);
+               debug("*** (%d) (%d) current_rdcc, best_rdcc\n",
+                       val, best_rdcc);
+
+               if ((result != 0) &&
+                   (val >= SDRAM_RDCC_RDSS_VAL(SDRAM_RDCC_RDSS_T2))) {
+                       if (((result == best_result) && (val < best_rdcc)) ||
+                           ((result > best_result) && (val <= best_rdcc))) {
+                               tcal.autocal.flags = 1;
+                               debug("*** (%d)(%d) result passed window "
+                                       "size: 0x%08x, rqfd = 0x%08x, "
+                                       "rffd = 0x%08x, rdcc = 0x%08x\n",
+                                       wdtr, clkp, result, ddrcal.rqfd,
+                                       ddrcal.rffd, ddrcal.rdcc);
+
                                /*
-                                * want the lowest Read Sample Cycle Select
+                                * Save the SDRAM_WRDTR and SDRAM_CLKTR
+                                * settings for the largest returned
+                                * RFFD passing window size.
                                 */
-                               val = (val & SDRAM_RDCC_RDSS_MASK) >> 30;
-                               debug("*** (%d) (%d) current_rdcc, best_rdcc\n",
-                                                       val, best_rdcc);
-                               if (val <= best_rdcc) {
-                                       best_rdcc = val;
-                                       tcal.clocks.wrdtr = wdtr;
-                                       tcal.clocks.clktr = clkp;
-                                       tcal.clocks.rdcc = (val << 30);
-                                       tcal.autocal.rqfd = ddrcal.rqfd;
-                                       tcal.autocal.rffd = ddrcal.rffd;
-                                       best_result = result;
+                               best_rdcc = val;
+                               tcal.clocks.wrdtr = wdtr;
+                               tcal.clocks.clktr = clkp;
+                               tcal.clocks.rdcc = SDRAM_RDCC_RDSS_ENCODE(val);
+                               tcal.autocal.rqfd = ddrcal.rqfd;
+                               tcal.autocal.rffd = ddrcal.rffd;
+                               best_result = result;
 
                                        if (verbose_lvl > 2) {
                                                printf("** (%d)(%d)  "
@@ -1133,9 +1171,8 @@ u32 DQS_autocalibration(void)
                                                       "loop FCSR: 0x%08x\n",
                                                        wdtr, clkp, val);
                                        }
-                               } /* if (val <= best_rdcc) */
-                       } /* if (result >= best_result) */
-               } /* if (result != 0) */
+                       }
+               } /* if ((result != 0) && (val >= (ddr_rdss_opt()))) */
                scan_list++;
        } /* while ((scan_list->wrdtr != -1) && (scan_list->clktr != -1)) */
 
@@ -1170,6 +1207,8 @@ u32 DQS_autocalibration(void)
 
                mtsdram(SDRAM_CLKTR, tcal.clocks.clktr << 30);
 
+               relock_memory_DLL();
+
                mfsdram(SDRAM_RQDC, rqdc_reg);
                rqdc_reg &= ~(SDRAM_RQDC_RQFD_MASK);
                mtsdram(SDRAM_RQDC, rqdc_reg |