openbcm

Git mirror of https://github.com/Broadcom-Network-Switching-Software/OpenBCM
git clone git://git.finwo.net/mirror/broadcom/openbcm
Log | Files | Refs | README

ddrtest.c (53447B)


      1 /*
      2  * 
      3  * This license is set out in https://raw.githubusercontent.com/Broadcom-Network-Switching-Software/OpenBCM/master/Legal/LICENSE file.
      4  * 
      5  * Copyright 2007-2019 Broadcom Inc. All rights reserved.
      6  */
      7 #include <shared/bsl.h>
      8 
      9 #include <sal/types.h>
     10 
     11 #include <sal/core/libc.h>
     12 #include <sal/core/boot.h>
     13 #include <sal/appl/sal.h>
     14 #include <sal/appl/io.h>
     15 #include <sal/appl/pci.h>
     16 #include <sal/appl/config.h>
     17 #include <shared/bsl.h>
     18 #include <appl/diag/system.h>
     19 #include <appl/diag/parse.h>
     20 #include <appl/diag/progress.h>
     21 #include <soc/mem.h>
     22 #include <soc/debug.h>
     23 #include <soc/l2x.h>
     24 #include <soc/shmoo_ddr40.h>
     25 #include <soc/phy/ddr40.h>
     26 #include <soc/shmoo_sjc16.h>
     27 #include <soc/phy/ydc_ddr_bist.h>
     28 
     29 #include "testlist.h"
     30 
     31 #ifdef BCM_DDR3_SUPPORT
     32 
     33 #define CI_DDR_MASK 0x3fffff /* [21:0] bit field for writes */
     34 #define C3_CI_DDR_MASK 0x7fffff /* [22:0] bit field for writes */
     35 
     36 #define DEFAULT_PATTERN 0xd0d1d0d1
     37 
     38 /* DDR Bist Flags*/
     39 #define DDR_BIST_CONS_ADDR_8_BANKS     (0x01)
     40 #define DDR_BIST_ADDRESS_SHIFT_MODE    (0X02)
     41 #define DDR_BIST_INFINITE              (0x04)
     42 #define DDR_BIST_ALL_ADDRESS           (0x08)
     43 #define DDR_BIST_STOP                  (0x10)
     44 #define DDR_BIST_GET_DATA              (0x20)
     45 #define DDR_BIST_TWO_ADDRESS_MODE      (0x40)
     46 
     47 typedef enum _DDRMemTests {
     48   DDR_ALL_TESTS = 0,
     49   DDR_STANDARD_TEST = 1,
     50   DATA_BUS_WALKING_ONES = 2,
     51   DATA_BUS_WALKING_ZEROS = 3,
     52   DDR_DATA_EQ_ADDR = 4,
     53   DDR_INDIRECT_TEST = 5,
     54   /* leave as last */
     55   MEM_TEST_LAST
     56 } DDRMemTests_t;
     57 
     58 typedef enum ddr_bist_data_pattern_mode {
     59     /*
     60      * costum pattern. Use the pattern as is.
     61      */
     62     DRAM_BIST_DATA_PATTERN_CUSTOM = 0,
     63     /*
     64      *  The PRBS will be used to generate the pattern towards
     65      *  the DRAM.
     66      */
     67     DRAM_BIST_DATA_PATTERN_RANDOM_PRBS = 1,
     68     /*
     69      *  Fill the data to write by 1010101... (Bits). The DATA_MODE
     70      *  may use this data pattern in different ways see
     71      *  ARAD_DRAM_BIST_DATA_MODE. 
     72      */
     73     DRAM_BIST_DATA_PATTERN_DIFF = 2,
     74     /*
     75      *  Fill the data to write by 11111111... (Bits). The DATA_MODE
     76      *  may use this data pattern in different ways see
     77      *  ARAD_DRAM_BIST_DATA_MODE. Random mode ignores these
     78      *  values.
     79      */
     80     DRAM_BIST_DATA_PATTERN_ONE = 3,
     81     /*
     82      *  Fill the data to write by 00000000... (Bits). The DATA_MODE
     83      *  may use this data pattern in different ways see
     84      *  ARAD_DRAM_BIST_DATA_MODE. Random mode ignores these
     85      *  values.
     86      */
     87     DRAM_BIST_DATA_PATTERN_ZERO = 4,
     88     /*
     89      * A different bit is selected from pattern0 - pattern7 in an incremental manner.
     90      * The selected bit is duplicated on all of the dram data bus.
     91      */
     92     DRAM_BIST_DATA_PATTERN_BIT_MODE = 5,
     93     /*
     94      * data shift mode.
     95      * Every write/read command the data will be shifted 1 bit to the left in a cyclic manner.
     96      * The initial pattern is pattern0 which is duplicated 8 times.
     97      * This DATA_MODE create 8 consecutive dram transactions.
     98      */
     99     DRAM_BIST_DATA_PATTERN_SHIFT_MODE = 6,
    100     /*
    101      * data address mode.
    102      * Every command data will be equal to the address it is written to.
    103      */
    104     DRAM_BIST_DATA_PATTERN_ADDR_MODE = 7,
    105     /*
    106      * nof data pattern modes
    107      */
    108     DRAM_BIST_NOF_DATA_PATTERN_MODES = 8
    109 } ddr_bist_data_pattern_mode_t;
    110 
    111 #define DRAM_BIST_NOF_PATTERNS (8)
    112 
    113 typedef struct ddr_bist_test_run_info_s {
    114     /*
    115      *  Number of Write commands per cycle. Range 0-225. 0 then
    116      *  no write will be performed.
    117      */
    118     uint32 write_weight;
    119     /*
    120      *  Number of Read commands per cycle. Range 0-225. 0 then
    121      *  no write will be performed.
    122      */
    123     uint32 read_weight;
    124     /*
    125      * number of actions
    126      */
    127     uint32 bist_num_actions;
    128     /*
    129      *  Start address (offset) of the Bist test commands.
    130      *  The address must be a multiple of 32 Bytes.
    131      *  Units: Bytes. Range: 0 - DRAM size-32.
    132      */
    133     uint32 bist_start_address;
    134     /*
    135      *  End address (offset) of the Bist test commands. If end address is
    136      *  reached, address is reset to the initial write or read
    137      *  address. The format is the same as the start address.
    138      *  For example, for 1 Gb interface, set to 0x7FFFFE0.
    139      *  For 2 Gb interface, set to 0xFFFFFE0.
    140      */
    141 
    142     uint32 bist_end_address;
    143     /*
    144      * pattern info
    145      */
    146     ddr_bist_data_pattern_mode_t pattern_mode;
    147     /*
    148      * patterns
    149      */
    150     uint32 pattern[DRAM_BIST_NOF_PATTERNS];   
    151     /*
    152      * flags
    153      */
    154     uint32 ddr_bist_flags;
    155 } ddr_bist_test_run_info_t;
    156 
    157 const char* DDRMemTestStr[] = {"All DDR tests",
    158                         "DDR Standard burst",
    159                         "DDR walking ones on data bus",
    160                         "DDR walking zeros on data bus",
    161                         "DDR Data == Address",
    162                         "DDR Indirect pattern"};
    163 
    164 typedef struct ddr_test_params_s {
    165     int unit;
    166     DDRMemTests_t ddr_test_mode;
    167     int32 pattern;
    168     int ci_interface;
    169     int ddr_start_addr;
    170     int ddr_step_addr;
    171     int ddr_burst;
    172     int ddr_iter;
    173     int bank;
    174     int max_row;
    175     int max_col;
    176     int write_test;
    177     int read_test;
    178     soc_pbmp_t dram_ndx;
    179     ddr_bist_test_run_info_t run_info;
    180 } ddr_test_params_t;
    181 
    182 static ddr_test_params_t      *ddr_test_params[SOC_MAX_NUM_DEVICES];
    183 
    184 char ddr_test_usage[] = 
    185 "DDR Memory Test Usage:\n"
    186 #ifdef COMPILER_STRING_CONST_LIMIT
    187 "MemTest=<0,1,2,3,4> <args>\n"
    188 #else
    189 "MemTest=<0,1,2,3,4> where:\n"
    190 "   0 - All Standard tests\n"
    191 "   1 - Standard DDR burst write/read test\n"
    192 "   2 - Walking ones on data bus\n"
    193 "   3 - Walking zeros on data bus\n"
    194 "   4 - DDR DATA == ADDRESS test \n"
    195 "   5 - Indirect Memory Test\n"
    196 "                            \n"
    197 " Options for Standard DDR test: \n"
    198 "  StartAddr=<0xvalue>     specifies starting memory address\n"
    199 "  AddrStepInc=<0xvalue>   specifies address step \n"
    200 "  BurstSize=<value>       number of burst to write, followed by same number of reads\n"
    201 "  Pattern=<0xvalue>       memory test pattern \n"
    202 "                                             \n"
    203 " Options for all tests except indirect:      \n"
    204 "  Iterations=<value>      how many times to run test, defaults to one\n"
    205 "                         note: iterations=0 will run test continuously \n"
    206 "  CI=<value>              CI interface to run test on, default is all of them\n"
    207 "                                             \n"
    208 " Indirect Memory Test options:\n"
    209 "  Pattern=<0xvalue> if not specifed address will be used as data \n"
    210 "  Bank=<value>      specifies bank within DDR to test (0-7)\n"
    211 "  MaxRow=<value>    specified the maximum row within the bank to test \n"
    212 "  MaxCol=<value>    specified the maximum column within the bank to test \n"
    213 "  CI=<value>        what ci interface to run test on \n"
    214 "                                             \n"
    215 "NOTE: If MemTest is not specified or is set to a value of 0,\n"
    216 "      then all tests (except indirect) are run\n"
    217 #endif
    218 ;
    219 
    220 int
    221 ddr_test_init(int unit, args_t *a, void **p)
    222 {
    223     ddr_test_params_t *dt;
    224     int mem_test;
    225     parse_table_t pt;
    226     int rv = -1;
    227     int ddr_step_addr;
    228     int ddr_start_addr;
    229     int ddr_test_count;
    230     int ddr_burst_size;
    231     int ci_interface;
    232     int bank, max_row, max_col;
    233     int pattern;
    234     int write_only, read_only;
    235 
    236     dt = ddr_test_params[unit];
    237     if (dt == NULL) {
    238         dt = sal_alloc(sizeof(ddr_test_params_t), "ddrtest");
    239         if (dt == NULL) {
    240             LOG_ERROR(BSL_LS_APPL_TESTS,
    241                       (BSL_META_U(unit,
    242                                   "%s: cannot allocate memory test data\n"), ARG_CMD(a)));
    243             return -1;
    244         }
    245         sal_memset(dt, 0, sizeof(ddr_test_params_t));
    246         ddr_test_params[unit] = dt;
    247     }
    248 
    249     parse_table_init(unit, &pt);
    250 
    251     parse_table_add(&pt, "MemTest", PQ_INT, (void *) 0,
    252           &mem_test, NULL);
    253     parse_table_add(&pt, "StartAddr", PQ_INT, (void*) 0,
    254             &ddr_start_addr, NULL);
    255     parse_table_add(&pt, "AddrStepInc", PQ_INT, (void *) 1,
    256             &ddr_step_addr, NULL);
    257     parse_table_add(&pt, "WriteOnly", PQ_INT, (void *) (0),
    258             &write_only, NULL);
    259     parse_table_add(&pt, "ReadOnly", PQ_INT, (void *) (0),
    260             &read_only, NULL);
    261         parse_table_add(&pt, "BurstSize", PQ_INT, (void *) (256),
    262             &ddr_burst_size, NULL);
    263 
    264 
    265     parse_table_add(&pt, "Pattern", PQ_INT, (void *) (DEFAULT_PATTERN),
    266           &pattern, NULL);
    267 
    268     parse_table_add(&pt, "Iterations", PQ_INT, (void *) 1,
    269             &ddr_test_count, NULL);
    270     parse_table_add(&pt, "CI", PQ_INT, (void *) (-1),
    271             &ci_interface, NULL);
    272     parse_table_add(&pt, "Bank", PQ_INT, (void *) (-1),
    273             &bank, NULL);
    274     parse_table_add(&pt, "MaxRow", PQ_INT, INT_TO_PTR(SOC_DDR3_NUM_ROWS(unit)),
    275             &max_row, NULL);
    276     parse_table_add(&pt, "MaxCol", PQ_INT, INT_TO_PTR(SOC_DDR3_NUM_COLUMNS(unit)),
    277             &max_col, NULL);
    278 
    279     if (parse_arg_eq(a, &pt) < 0) {
    280         cli_out("%s: Invalid option: %s\n",
    281                 ARG_CMD(a), ARG_CUR(a));
    282         cli_out("%s\n",ddr_test_usage);
    283         goto done;
    284     }
    285 
    286     if (ARG_CNT(a) != 0) {
    287         cli_out("%s: extra options starting with \"%s\"\n",
    288                 ARG_CMD(a), ARG_CUR(a));
    289         cli_out("%s\n",ddr_test_usage);
    290         goto done;
    291     }
    292 
    293     dt->unit = unit;
    294     dt->pattern = pattern;
    295     dt->ci_interface = ci_interface;
    296     dt->ddr_start_addr = ddr_start_addr;
    297     dt->ddr_step_addr = ddr_step_addr;
    298     dt->ddr_burst = ddr_burst_size;
    299     dt->ddr_iter = ddr_test_count;
    300     dt->ddr_test_mode = mem_test;
    301     dt->bank = bank;
    302     dt->max_row = max_row;
    303     dt->max_col = max_col;
    304     dt->write_test = write_only;
    305     dt->read_test = read_only;
    306     dt->max_col = max_col;
    307     *p = dt;
    308     rv = 0;
    309 
    310     done:
    311        parse_arg_eq_done(&pt);
    312        return rv;
    313 }
    314 
    315 int StartDDRFunctionalTest(ddr_test_params_t *testparams,
    316                             int ci_start,
    317                             int ci_end,
    318                             DDRMemTests_t mode) {
    319 
    320     uint32 uData, ddr_iter;
    321     int ci, unit;
    322     ddr_test_params_t *dt = testparams;
    323     uint32 uDDRMask;
    324 
    325     unit = dt->unit;
    326     uDDRMask = CI_DDR_MASK;
    327     ddr_iter = dt->ddr_iter & uDDRMask;
    328 
    329     /*
    330     * Be able to Show test results for each iteration, unless ddr_iter == 0
    331     * then results are displayed after some interval
    332     */
    333 
    334     if (ddr_iter != 0) ddr_iter = 1;
    335 
    336     /*
    337     * Set the test mode as follows:
    338     * 0 - Standard writing burst of data and alt_data, followed by reads
    339     * 1 - Walking ones test on the data lines (test data not used).
    340     * 2 - Walking zeros on the test data lines (test data not used). 
    341     * 3 - Used Data == Address (test data not used)
    342     * - clear ram_done
    343     * - clear ram_test
    344     * - clear ram_test_fail
    345     * - set ram_test to initiate test
    346     */
    347 
    348     uData = 0;
    349     for (ci = ci_start; ci < ci_end; ci++) {
    350     
    351         WRITE_DDR40_PHY_WORD_LANE_0_READ_FIFO_CLEARr(unit, ci, 0);
    352         WRITE_DDR40_PHY_WORD_LANE_1_READ_FIFO_CLEARr(unit, ci, 0);
    353         
    354         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_ITERr(unit, ci, ddr_iter));
    355         SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit, ci, &uData));
    356         soc_reg_field_set(unit, CI_DDR_TESTr, &uData, MODEf,(mode-1));
    357         soc_reg_field_set(unit, CI_DDR_TESTr, &uData, RAM_DONEf, 1);      /* W1TC */
    358         soc_reg_field_set(unit, CI_DDR_TESTr, &uData, RAM_TESTf, 0);      /* clear */
    359         soc_reg_field_set(unit, CI_DDR_TESTr, &uData, RAM_TEST_FAILf, 1); /* W1TC */
    360         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TESTr(unit, ci, uData));
    361 
    362         /* set ram_test - to start the test */
    363         SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit, ci, &uData));
    364         soc_reg_field_set(unit, CI_DDR_TESTr, &uData, RAM_TESTf, 1);
    365         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TESTr(unit, ci, uData));
    366     }
    367 
    368     return BCM_E_NONE;
    369 }
    370 
    371 
    372 int CheckDDRFunctionalTest(ddr_test_params_t *testparams,
    373                             int ci_start, int ci_end,
    374                             uint64 *pFailedCount,
    375                             uint64 *pTimedOutCount,
    376                             uint64 *pPassedCount) {
    377     int unit, ci, rv = BCM_E_NONE;
    378     uint32 ddr_iter, uData = 0;
    379     uint8 bFailed = 0;
    380     uint8 bDone = 0;
    381     ddr_test_params_t *dt = testparams;
    382     uint32 uDDRMask;
    383 
    384     unit = dt->unit;
    385     uDDRMask = CI_DDR_MASK;
    386     ddr_iter = dt->ddr_iter & uDDRMask;
    387 
    388     for (ci = ci_start; ci < ci_end; ci++) {
    389         SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit, ci, &uData));
    390         bFailed = soc_reg_field_get(unit,CI_DDR_TESTr, uData, RAM_TEST_FAILf);
    391         bDone = soc_reg_field_get(unit, CI_DDR_TESTr, uData, RAM_DONEf);
    392         if (bFailed) {
    393           COMPILER_64_ADD_32(pFailedCount[ci], 1); rv = -1;
    394         } else if (bDone == 0 && ddr_iter != 0) {
    395           COMPILER_64_ADD_32(pTimedOutCount[ci], 1); rv = -1;
    396         } else {
    397           COMPILER_64_ADD_32(pPassedCount[ci], 1);
    398         }
    399     }
    400     return rv;
    401 }
    402 
    403 
    404 /* show results for each iteration */
    405 int DumpDDRResults(int unit,
    406                     int ci_start, int ci_end,
    407                     int iter_count,
    408                     uint64 *pFailedCount,
    409                     uint64 *pTimedOutCount,
    410                     uint64 *pPassedCount) {
    411     int i, ci;
    412     uint32 uFailedAddr=0;
    413     uint32 uFailedData[8] = {0};
    414     uint32 uData = 0;
    415     uint8 bFailed = 0;
    416 
    417     /* print results for each iteration */
    418     for(ci = ci_start; ci < ci_end; ci++) {
    419         if (iter_count != -1 ) {
    420             LOG_INFO(BSL_LS_APPL_TESTS,
    421                      (BSL_META_U(unit,
    422                                  "Iteration:%d CI%d Fail:0x%08x%08x Pass:0x%08x%08x Timedout:0x%08x%08x\n"),
    423                       iter_count,ci,
    424                       COMPILER_64_HI(pFailedCount[ci]),COMPILER_64_LO(pFailedCount[ci]),
    425                       COMPILER_64_HI(pPassedCount[ci]),COMPILER_64_LO(pPassedCount[ci]),
    426                       COMPILER_64_HI(pTimedOutCount[ci]),COMPILER_64_LO(pTimedOutCount[ci])));
    427         } else { /* running continuously */
    428             LOG_INFO(BSL_LS_APPL_TESTS,
    429                      (BSL_META_U(unit,
    430                                  "CI%d Fail:0x%08x%08x Pass:0x%08x%08x \n"),ci,
    431                       COMPILER_64_HI(pFailedCount[ci]),COMPILER_64_LO(pFailedCount[ci]),
    432                       COMPILER_64_HI(pPassedCount[ci]),COMPILER_64_LO(pPassedCount[ci])));
    433         }
    434         /* if this CI interface failed, print the failing addr and data */
    435         SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit, ci, &uData));
    436         bFailed = soc_reg_field_get(unit, CI_DDR_TESTr, uData, RAM_TEST_FAILf);
    437         if (bFailed) {
    438             SOC_IF_ERROR_RETURN(READ_CI_FAILED_ADDRr(unit,ci,&uFailedAddr));
    439             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA0r(unit,ci,&uFailedData[0]));
    440             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA1r(unit,ci,&uFailedData[1]));
    441             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA2r(unit,ci,&uFailedData[2]));
    442             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA3r(unit,ci,&uFailedData[3]));
    443             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA4r(unit,ci,&uFailedData[4]));
    444             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA5r(unit,ci,&uFailedData[5]));
    445             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA6r(unit,ci,&uFailedData[6]));
    446             SOC_IF_ERROR_RETURN(READ_CI_DDR_TEST_FAILED_DATA7r(unit,ci,&uFailedData[7]));
    447             cli_out("CI%d Failing address = (0x%08x)\n",ci,uFailedAddr);
    448             for (i = 0; i < 8; i++) {
    449                 if (i == 4) {
    450                     cli_out("\n");
    451                 }
    452                 cli_out("failing_data_%d = (0x%08x)  ", i, uFailedData[i]);
    453             }
    454             cli_out("\n");
    455 
    456             /* clear the failing status bit for this ci */
    457             SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit, ci, &uData));
    458             soc_reg_field_set(unit, CI_DDR_TESTr, &uData, RAM_TEST_FAILf, 1); /* W1TC */
    459             SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TESTr(unit, ci, uData));
    460         }
    461         
    462         WRITE_DDR40_PHY_WORD_LANE_0_READ_FIFO_CLEARr(unit, ci, 0);
    463         WRITE_DDR40_PHY_WORD_LANE_1_READ_FIFO_CLEARr(unit, ci, 0);
    464     }
    465     return BCM_E_NONE;
    466 }
    467 
    468 /* run single DDR test */
    469 int DDRTest(ddr_test_params_t *testparams) {
    470     ddr_test_params_t *dt = testparams;
    471     DDRMemTests_t ddr_test;
    472     int rv, unit, iter_count, ci, ci_start, ci_end, stat=0;
    473     uint32 uData=0, pattern, uDDRIter, uStartAddr, uStepSize, uDDRBurstSize;
    474     uint64 uFailedCount[SOC_MAX_NUM_CI_BLKS];
    475     uint64 uPassedCount[SOC_MAX_NUM_CI_BLKS];
    476     uint64 uTimedOutCount[SOC_MAX_NUM_CI_BLKS];
    477     uint32 uDDRMask;
    478 
    479     for (ci = 0; ci < SOC_MAX_NUM_CI_BLKS; ci++) {
    480         COMPILER_64_ZERO(uFailedCount[ci]);
    481         COMPILER_64_ZERO(uPassedCount[ci]);
    482         COMPILER_64_ZERO(uTimedOutCount[ci]);
    483     }
    484 
    485     unit = dt->unit;
    486     uDDRMask = CI_DDR_MASK;
    487 
    488     if (dt->ci_interface < 0) {
    489         /* test all of them */
    490         ci_start = 0; 
    491         ci_end = 3; 
    492     } else {
    493         ci_start = dt->ci_interface;
    494         ci_end = ci_start+1;
    495         LOG_WARN(BSL_LS_APPL_TESTS,
    496                  (BSL_META_U(unit,
    497                              "Testing only CI%d interface\n"),ci_start));
    498     }
    499     ddr_test = dt->ddr_test_mode;
    500     uDDRIter = dt->ddr_iter & uDDRMask;
    501 
    502     LOG_INFO(BSL_LS_APPL_TESTS,
    503              (BSL_META("Running Test %s\n"), DDRMemTestStr[ddr_test]));
    504 
    505     if (dt->pattern != DEFAULT_PATTERN ) {
    506         pattern = dt->pattern & 0xffffffff;
    507         if (DDR_STANDARD_TEST != ddr_test) {
    508             LOG_WARN(BSL_LS_APPL_TESTS,
    509                      (BSL_META_U(unit,
    510                                  "NOTE: Test data is not used during data bus test\n")));
    511         }
    512     } else {
    513         /* no pattern specified use alternating 0101.. pattern */
    514         pattern = 0x55555555;
    515     }
    516 
    517     uStartAddr = dt->ddr_start_addr & uDDRMask;
    518     uStepSize = dt->ddr_step_addr & uDDRMask;
    519     uDDRBurstSize = dt->ddr_burst & uDDRMask;
    520 
    521     if (DDR_STANDARD_TEST == ddr_test ||
    522         DDR_DATA_EQ_ADDR == ddr_test) {
    523         LOG_INFO(BSL_LS_APPL_TESTS,
    524                  (BSL_META("start_addr=0x%x,addr_step_inc=0x%x,burst_size=%d\n"),uStartAddr,uStepSize,uDDRBurstSize));
    525         if (DDR_STANDARD_TEST == ddr_test) {
    526             LOG_INFO(BSL_LS_APPL_TESTS,
    527                      (BSL_META("using pattern=0x%8x, and alt_pattern=0x%8x\n"),pattern,~pattern));
    528         }
    529     }
    530 
    531     for (ci = ci_start; ci < ci_end; ci++) {
    532       /* set test specific attributes */
    533       /* SOC_IF_ERROR_RETURN(WRITE_CI_DEBUGr(unit,ci,0x1)); ? inject auto refresh */
    534       SOC_IF_ERROR_RETURN(WRITE_CI_DDR_STARTr(unit,ci,uStartAddr));
    535       SOC_IF_ERROR_RETURN(WRITE_CI_DDR_STEPr(unit,ci,uStepSize));
    536       SOC_IF_ERROR_RETURN(WRITE_CI_DDR_BURSTr(unit,ci,uDDRBurstSize));
    537       /* only STANDARD_DDR test uses pattern data */
    538       if (DDR_STANDARD_TEST == ddr_test) {
    539         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA0r(unit,ci,pattern));
    540         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA1r(unit,ci,pattern));
    541         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA2r(unit,ci,pattern));
    542         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA3r(unit,ci,pattern));
    543         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA4r(unit,ci,pattern));
    544         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA5r(unit,ci,pattern));
    545         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA6r(unit,ci,pattern));
    546         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_DATA7r(unit,ci,pattern));
    547         /* set the alt_data */
    548         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA0r(unit,ci,~pattern));
    549         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA1r(unit,ci,~pattern));
    550         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA2r(unit,ci,~pattern));
    551         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA3r(unit,ci,~pattern));
    552         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA4r(unit,ci,~pattern));
    553         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA5r(unit,ci,~pattern));
    554         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA6r(unit,ci,~pattern));
    555         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TEST_ALT_DATA7r(unit,ci,~pattern));
    556         SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit,ci,&uData));
    557       }
    558     }
    559 
    560     /* Run the particular test uDDRIter times */
    561     for(iter_count = 0; iter_count < uDDRIter; iter_count++) {
    562         /* start the test for this iteration */
    563         if (( rv = StartDDRFunctionalTest(dt, ci_start,
    564                                           ci_end, ddr_test)) < 0 ) {
    565             LOG_ERROR(BSL_LS_APPL_TESTS,
    566                       (BSL_META_U(unit,
    567                                   "%s failed to start %s test.\n"),SOC_CHIP_STRING(unit),
    568                        DDRMemTestStr[ddr_test]));
    569             return rv;
    570         }
    571         /* wait long enough for all ci's being tested to be done */
    572         sal_sleep(2);
    573 
    574         /* check the test results for this iteration */
    575         if (( rv = CheckDDRFunctionalTest(dt,
    576                                             ci_start, ci_end,
    577                                             uFailedCount,
    578                                             uTimedOutCount,
    579                                             uPassedCount)) < 0 ) {
    580           
    581             LOG_ERROR(BSL_LS_APPL_TESTS,
    582                       (BSL_META_U(unit,
    583                                   "%s failed %s test.\n"),SOC_CHIP_STRING(unit),
    584                        DDRMemTestStr[ddr_test]));
    585 
    586             /* one or more CI's failed
    587             * dump register debug info here
    588             */
    589             stat = -1;
    590         }
    591 
    592         /* display the results for this iteration */
    593         if (( rv = DumpDDRResults(unit,
    594                                     ci_start, ci_end,
    595                                     iter_count,
    596                                     uFailedCount,
    597                                     uTimedOutCount,
    598                                     uPassedCount)) < 0) {
    599             return rv;
    600         }
    601 
    602     }
    603 
    604     /* special case if ddr_iter == 0, run test continuously */
    605     if (uDDRIter == 0) {
    606         /* start the test to run continuously */
    607         if (( rv = StartDDRFunctionalTest(dt, ci_start,
    608                                           ci_end, ddr_test)) < 0 ) {
    609             LOG_ERROR(BSL_LS_APPL_TESTS,
    610                       (BSL_META_U(unit,
    611                                   "%s failed to start %s test.\n"),SOC_CHIP_STRING(unit),
    612                        DDRMemTestStr[ddr_test]));
    613             return rv;
    614         }
    615         cli_out("Running test continuously CTRL-C to STOP.. \n");
    616         while(1) {
    617 
    618             /* check results at some interval */
    619             sal_sleep(2);
    620 
    621             if (( rv = CheckDDRFunctionalTest(dt,
    622                                                 ci_start, ci_end,
    623                                                 uFailedCount,
    624                                                 uTimedOutCount,
    625                                                 uPassedCount)) < 0 ) {
    626               
    627                 LOG_ERROR(BSL_LS_APPL_TESTS,
    628                           (BSL_META_U(unit,
    629                                       "%s failed %s test.\n"),SOC_CHIP_STRING(unit),
    630                            DDRMemTestStr[ddr_test]));
    631             
    632                 /* one or more CI's failed
    633                 * dump register debug info here
    634                 */
    635                 stat = -1;
    636             }
    637 
    638             /* display results while test is running */
    639             if (( rv = DumpDDRResults(unit,
    640                                         ci_start, ci_end,
    641                                         -1,
    642                                         uFailedCount,
    643                                         uTimedOutCount,
    644                                         uPassedCount)) < 0) {
    645                 return rv;
    646             }
    647         }
    648     }
    649     
    650     /* clean up after test run */
    651     for (ci = ci_start; ci < ci_end; ci++) {
    652         SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit,ci,&uData));
    653         soc_reg_field_set(unit,CI_DDR_TESTr,&uData,RAM_DONEf,1);      /* W1TC */
    654         soc_reg_field_set(unit,CI_DDR_TESTr,&uData,RAM_TESTf,0);      /* clear */
    655         soc_reg_field_set(unit,CI_DDR_TESTr,&uData,RAM_TEST_FAILf,1); /* W1TC */
    656         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TESTr(unit,ci,uData));
    657     }
    658     
    659     return stat;
    660 }
    661 
    662 /* run DDR Indirect Pattern test */
    663 int DDRIndirectTest(ddr_test_params_t *testparams) {
    664     ddr_test_params_t *dt = testparams;
    665     uint8 bUseAddrAsData = FALSE;
    666     uint32 uDataWR[8] = {0};
    667     uint32 uDataRD[8] = {0};
    668     uint32 pla_addr, comp_data, pattern=0;
    669     uint32 row, max_row, col, max_col;
    670     int i, unit, bank, start_bank, end_bank, ci, ci_start, ci_end, stat;
    671 
    672     unit = dt->unit;
    673 
    674     if (dt->bank == -1) {
    675       start_bank = 0;
    676       end_bank = 8;
    677     } else {
    678       start_bank = dt->bank & 0x7;
    679       end_bank = start_bank+1;
    680     }
    681     
    682     if (dt->ci_interface < 0) {
    683       ci_start = 0; ci_end = SOC_DDR3_NUM_MEMORIES(unit);
    684     } else {
    685       ci_start = dt->ci_interface;
    686       ci_end = ci_start+1;
    687       LOG_WARN(BSL_LS_APPL_TESTS,
    688                (BSL_META_U(unit,
    689                            "Testing only CI%d interface\n"),ci_start));
    690     }
    691     
    692     /* if no pattern specified use the address as data */
    693     if (dt->pattern == -1) {
    694       bUseAddrAsData = TRUE;
    695     } else {
    696       pattern = dt->pattern & 0xffffffff;
    697     }
    698 
    699     max_row = (dt->max_row <= SOC_DDR3_NUM_ROWS(unit)) ?
    700                             dt->max_row : SOC_DDR3_NUM_ROWS(unit);
    701     max_col = (dt->max_col <= SOC_DDR3_NUM_COLUMNS(unit)) ?
    702                             dt->max_col : SOC_DDR3_NUM_COLUMNS(unit);
    703 
    704     for(ci=ci_start;ci<ci_end;ci++) {
    705         WRITE_DDR40_PHY_WORD_LANE_0_READ_FIFO_CLEARr(unit, ci, 0);
    706         WRITE_DDR40_PHY_WORD_LANE_1_READ_FIFO_CLEARr(unit, ci, 0);
    707         LOG_INFO(BSL_LS_APPL_TESTS,
    708                  (BSL_META("Filling ci%d\n"), ci));
    709         for (bank=start_bank;bank<end_bank;bank++) {
    710             for(row=0;row<max_row;row++) {
    711                 for (col=0;col<max_col;col++) {
    712                     pla_addr = bank;
    713                     pla_addr |= col << 3;
    714                     pla_addr |= row << 9;
    715                     for (i = 0; i < 8; i++ ) { 
    716                         if (bUseAddrAsData) {
    717                             uDataWR[i] = pla_addr;
    718                         } else {
    719                             uDataWR[i] = pattern;
    720                         }
    721                     }
    722                     LOG_INFO(BSL_LS_APPL_TESTS,
    723                              (BSL_META("Filling ci%d bank[%d],row[0x%x],cols[0x%x-0x%x] \n"),
    724                               ci,bank,row,col<<4,(col<<4)+0xf));
    725 
    726                     stat = soc_ddr40_write(unit,ci,pla_addr,uDataWR[0],uDataWR[1],uDataWR[2],
    727                              uDataWR[3],uDataWR[4],uDataWR[5],uDataWR[6], uDataWR[7]);
    728                     if (0 != stat) {
    729                         /* Write Error */
    730                         return stat;
    731                     }
    732                 }
    733             }
    734         }
    735     }
    736 
    737     /* Read back and compare, verify each CI's DDR Memory */
    738     for(ci=ci_start;ci<ci_end;ci++) {
    739         LOG_INFO(BSL_LS_APPL_TESTS,
    740                  (BSL_META("Verifying ci%d\n"), ci));
    741         for (bank=start_bank;bank<end_bank;bank++) {
    742             for(row=0;row<max_row;row++) {
    743                 for (col=0;col<max_col;col++) {
    744                     pla_addr = bank;
    745                     pla_addr |= col << 3;
    746                     pla_addr |= row << 9;
    747                     LOG_INFO(BSL_LS_APPL_TESTS,
    748                              (BSL_META("Verifing ci%d bank[%d],row[0x%x],cols[0x%x-0x%x] \n"),
    749                               ci,bank,row,col<<4,(col<<4)+0xf));
    750                     stat = soc_ddr40_read(unit,ci,pla_addr,&uDataRD[0],&uDataRD[1],&uDataRD[2],
    751                              &uDataRD[3],&uDataRD[4],&uDataRD[5],&uDataRD[6],&uDataRD[7]); 
    752                     if (0 != stat) {
    753                         /* Read Error */
    754                         return stat;
    755                     }
    756                     /* check the data */
    757                     for (i = 0; i < 8; i++ ) {
    758                         comp_data = bUseAddrAsData ? pla_addr : pattern;
    759                         if (uDataRD[i] != comp_data) {
    760                             LOG_ERROR(BSL_LS_APPL_TESTS,
    761                                       (BSL_META_U(unit,
    762                                                   "Data compare failure at "
    763                                                   "pla_addr:(0x%x)\n"),pla_addr));
    764                             LOG_ERROR(BSL_LS_APPL_TESTS,
    765                                       (BSL_META_U(unit,
    766                                                   "Expected (0x%x) got (0x%x)\n"),
    767                                        comp_data,uDataRD[i]));
    768                             /* Compare Error */
    769                             return -1;
    770                         }
    771                     }
    772                 }
    773             }
    774         }
    775         WRITE_DDR40_PHY_WORD_LANE_0_READ_FIFO_CLEARr(unit, ci, 0);
    776         WRITE_DDR40_PHY_WORD_LANE_1_READ_FIFO_CLEARr(unit, ci, 0);
    777     }
    778 
    779     return 0;
    780 }
    781 
    782 int
    783 ddr_test(int unit, args_t *a, void *p)
    784 {
    785     ddr_test_params_t *dt = p;
    786     DDRMemTests_t ddr_test = dt->ddr_test_mode;
    787     int mem_test, rv = 0;
    788 
    789     if (DDR_ALL_TESTS == ddr_test) {
    790         /* All Tests */
    791         for(mem_test = 1; mem_test < MEM_TEST_LAST; mem_test++) {
    792             if (DDR_INDIRECT_TEST == mem_test) {
    793                 /* skip the indirect test -- takes too long */
    794                 continue;
    795             }
    796             dt->ddr_test_mode = mem_test;
    797             if (DDRTest(dt) != 0) {
    798                 rv = -1;
    799             }
    800         }
    801         return rv;
    802     } else if (DDR_INDIRECT_TEST == ddr_test) {
    803         return DDRIndirectTest(dt);
    804     } else {
    805         return DDRTest(dt);
    806     }
    807 }
    808 
    809 int
    810 ddr_test_done(int unit, void *p)
    811 {
    812     ddr_test_params_t *dt = p;
    813     uint32 uData=0;
    814     int ci, ci_start, ci_end;
    815     if (dt->ci_interface < 0) {
    816         /* test all of them */
    817         ci_start = 0;
    818         ci_end = 3; 
    819     } else {
    820         ci_start = dt->ci_interface;
    821         ci_end = ci_start+1;
    822     }
    823     /* stop the test by turning off ram_test */
    824     cli_out("Stopping Test.\n");
    825     for (ci = ci_start; ci < ci_end; ci++) {
    826         SOC_IF_ERROR_RETURN(READ_CI_DDR_TESTr(unit, ci, &uData));
    827         soc_reg_field_set(unit, CI_DDR_TESTr, &uData, RAM_TESTf, 0);
    828         SOC_IF_ERROR_RETURN(WRITE_CI_DDR_TESTr(unit, ci, uData));
    829     }
    830     LOG_INFO(BSL_LS_APPL_TESTS,
    831              (BSL_META_U(unit,
    832                          "DDR Mem Tests Done\n")));
    833     sal_free(ddr_test_params[unit]);
    834     ddr_test_params[unit] = NULL;
    835     return 0;
    836 }
    837 
    838 #if defined(BCM_KATANA2_SUPPORT)
    839 int _ddr_bist_configure(int unit, int ci, ddr_bist_test_run_info_t *info, uint32 *bist_pattern) {
    840     uint32 reg_val;
    841     int i;
    842     const static soc_reg_t bist_pattern_words_reg[DRAM_BIST_NOF_PATTERNS] = {BISTPATTERNWORD0r, BISTPATTERNWORD1r, BISTPATTERNWORD2r,
    843                     BISTPATTERNWORD3r, BISTPATTERNWORD4r, BISTPATTERNWORD5r, BISTPATTERNWORD6r, BISTPATTERNWORD7r};
    844 
    845     const static soc_field_t bist_pattern_words_field[DRAM_BIST_NOF_PATTERNS] = {BISTPATTERN0f, BISTPATTERN1f, BISTPATTERN2f,
    846                        BISTPATTERN3f, BISTPATTERN4f, BISTPATTERN5f, BISTPATTERN6f, BISTPATTERN7f};
    847 
    848     SOC_IF_ERROR_RETURN(READ_BISTCONFIGURATIONSr(unit,ci,&reg_val));
    849     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, WRITEWEIGHTf, info->write_weight);
    850     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, READWEIGHTf, info->read_weight);
    851     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, PATTERNBITMODEf, 
    852                                 (info->pattern_mode == DRAM_BIST_DATA_PATTERN_BIT_MODE) ? 1 : 0);
    853     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, TWOADDRMODEf,
    854                                 (info->ddr_bist_flags & DDR_BIST_TWO_ADDRESS_MODE) ? 1 : 0);
    855     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, PRBSMODEf,
    856                                 (info->pattern_mode == DRAM_BIST_DATA_PATTERN_RANDOM_PRBS) ? 1 : 0);
    857     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, CONSADDR8BANKSf,
    858                                 (info->ddr_bist_flags & DDR_BIST_CONS_ADDR_8_BANKS) ? 1 : 0);
    859     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, ADDRESSSHIFTMODEf,
    860                                 (info->ddr_bist_flags & DDR_BIST_ADDRESS_SHIFT_MODE) ? 1 : 0);
    861     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, DATASHIFTMODEf,
    862                                 (info->pattern_mode == DRAM_BIST_DATA_PATTERN_SHIFT_MODE) ? 1 : 0);
    863     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, DATAADDRMODEf,
    864                                 (info->pattern_mode == DRAM_BIST_DATA_PATTERN_ADDR_MODE) ? 1 : 0);
    865     soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, INDWRRDADDRMODEf, 1);
    866     SOC_IF_ERROR_RETURN(WRITE_BISTCONFIGURATIONSr(unit,ci,reg_val));
    867 
    868     SOC_IF_ERROR_RETURN(READ_BISTNUMBEROFACTIONSr(unit,ci,&reg_val));
    869     soc_reg_field_set(unit, BISTNUMBEROFACTIONSr, &reg_val, BISTNUMACTIONSf,
    870                                         (info->ddr_bist_flags & DDR_BIST_INFINITE) ? 0 : info->bist_num_actions);
    871     SOC_IF_ERROR_RETURN(WRITE_BISTNUMBEROFACTIONSr(unit,ci,reg_val));
    872 
    873     SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTSTARTADDRESSr, ci, 0, &reg_val));
    874     soc_reg_field_set(unit, BISTSTARTADDRESSr, &reg_val, BISTSTARTADDRESSf,
    875                                 info->bist_start_address);
    876     SOC_IF_ERROR_RETURN(soc_reg32_set(unit, BISTSTARTADDRESSr, ci, 0, reg_val));
    877 
    878     SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTENDADDRESSr, ci, 0, &reg_val));
    879     soc_reg_field_set(unit, BISTENDADDRESSr, &reg_val, BISTENDADDRESSf,
    880                                 info->bist_end_address);
    881     SOC_IF_ERROR_RETURN(soc_reg32_set(unit, BISTENDADDRESSr, ci, 0, reg_val));
    882 
    883     for(i=0; i < DRAM_BIST_NOF_PATTERNS; ++i) {
    884         SOC_IF_ERROR_RETURN(soc_reg32_get(unit, bist_pattern_words_reg[i], ci, 0, &reg_val));
    885         soc_reg_field_set(unit, bist_pattern_words_reg[i], &reg_val, bist_pattern_words_field[i], bist_pattern[i]);
    886         SOC_IF_ERROR_RETURN(soc_reg32_set(unit, bist_pattern_words_reg[i], ci, 0, reg_val));
    887     }
    888 
    889     return BCM_E_NONE;
    890 
    891 }
    892 
    893 int _ddr_bist_action(int unit, int ci, uint8  is_infinite, uint8  stop) {
    894   uint32 reg_val,to_usec;
    895   int done=0;
    896   soc_timeout_t to;
    897 
    898   if (stop == FALSE) {
    899       SOC_IF_ERROR_RETURN(READ_BISTCONFIGURATIONSr(unit,ci,&reg_val));
    900       soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, BISTENf, 0);
    901       SOC_IF_ERROR_RETURN(WRITE_BISTCONFIGURATIONSr(unit,ci,reg_val));
    902       SOC_IF_ERROR_RETURN(READ_BISTCONFIGURATIONSr(unit,ci,&reg_val));
    903       soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, BISTENf, 1);
    904       SOC_IF_ERROR_RETURN(WRITE_BISTCONFIGURATIONSr(unit,ci,reg_val));
    905   }
    906 
    907   if (is_infinite == FALSE && stop == FALSE) {  
    908     to_usec = SAL_BOOT_QUICKTURN ? 5000000 : 200000;
    909 
    910     soc_timeout_init(&to, to_usec, 0);
    911     while (!soc_timeout_check(&to)) {
    912 
    913         READ_BISTSTATUSESr(unit, ci, &reg_val);
    914         done = soc_reg_field_get(unit, BISTSTATUSESr,
    915                                    reg_val, BISTFINISHEDf);
    916         if (done) {
    917             break;
    918         }
    919         sal_usleep(1000);
    920     }
    921     if (!done) {
    922         return BCM_E_TIMEOUT;
    923     }
    924   }
    925 
    926   if (is_infinite == FALSE || stop == TRUE) {
    927       SOC_IF_ERROR_RETURN(READ_BISTCONFIGURATIONSr(unit,ci,&reg_val));
    928       soc_reg_field_set(unit, BISTCONFIGURATIONSr, &reg_val, BISTENf, 0);
    929       SOC_IF_ERROR_RETURN(WRITE_BISTCONFIGURATIONSr(unit,ci,reg_val));
    930   }
    931 
    932   return BCM_E_NONE;
    933 }
    934 
    935 int _ddr_bist_test_start(int unit, int ci, ddr_bist_test_run_info_t *info) {
    936     int i;
    937     uint32 pattern_lcl[DRAM_BIST_NOF_PATTERNS];
    938 
    939     if(info->pattern_mode == DRAM_BIST_DATA_PATTERN_DIFF) {
    940         for(i=0; i <  DRAM_BIST_NOF_PATTERNS; ++i) {
    941             pattern_lcl[i] = 0x55555555;
    942         }
    943     } else if(info->pattern_mode == DRAM_BIST_DATA_PATTERN_ONE) {
    944         for(i=0; i <  DRAM_BIST_NOF_PATTERNS; ++i) {
    945             pattern_lcl[i] = 0xffffffff;
    946         }
    947     } else if(info->pattern_mode == DRAM_BIST_DATA_PATTERN_ZERO) {
    948         for(i=0; i <  DRAM_BIST_NOF_PATTERNS; ++i) {
    949             pattern_lcl[i] = 0x00000000;
    950         }
    951     } else {
    952         for(i=0; i <  DRAM_BIST_NOF_PATTERNS; ++i) {
    953             pattern_lcl[i] = info->pattern[i];
    954         }
    955     }
    956 
    957     if((info->ddr_bist_flags & (DDR_BIST_STOP | DDR_BIST_GET_DATA)) == 0) {
    958          /* If one of this flags in set - don't configure */
    959         if (_ddr_bist_configure(unit, ci, info, pattern_lcl) < 0) {
    960             return BCM_E_FAIL;
    961         }
    962      }
    963      if((info->ddr_bist_flags & DDR_BIST_GET_DATA) == 0) {
    964          if( _ddr_bist_action(unit, ci,
    965                  (info->ddr_bist_flags & DDR_BIST_INFINITE) ? TRUE : FALSE,
    966                  (info->ddr_bist_flags & DDR_BIST_STOP) ? TRUE : FALSE  ) < 0) {
    967              return BCM_E_FAIL;
    968          }
    969     }
    970 
    971     return BCM_E_NONE;
    972 }
    973 
    974 #endif /* BCM_KATANA2_SUPPORT */
    975 #endif /* BCM_DDR3_SUPPORT */
    976 
    977 #if defined(BCM_DDR3_SUPPORT) || defined(BCM_PETRA_SUPPORT)
    978 
    979 int
    980 ddr_bist_test_init(int unit, args_t *a, void **p)
    981 {
    982     ddr_test_params_t *dt;
    983     parse_table_t pt;
    984     char* dram_ndx_srt=NULL;
    985     int rv = BCM_E_UNAVAIL;
    986     int i;
    987     uint32 use_default_test, cons_addr_8_banks, address_shift_mode;
    988     uint32 infinite, all_adress, stop, get_data, two_addr_mode;
    989 
    990 #ifdef BCM_PETRA_SUPPORT
    991     if (SOC_IS_ARAD(unit) || SOC_IS_DPP_DRC_COMBO28(unit)) {
    992         return arad_bist_test_init(unit, a, p);
    993     }
    994 #endif
    995 
    996     dt = ddr_test_params[unit];
    997     if (dt == NULL) {
    998         dt = sal_alloc(sizeof(ddr_test_params_t), "ddrtest");
    999         if (dt == NULL) {
   1000             LOG_ERROR(BSL_LS_APPL_TESTS,
   1001                       (BSL_META_U(unit,
   1002                                   "%s: cannot allocate memory test data\n"), ARG_CMD(a)));
   1003             return -1;
   1004         }
   1005         sal_memset(dt, 0, sizeof(ddr_test_params_t));
   1006         ddr_test_params[unit] = dt;
   1007     }
   1008     
   1009         if(ARG_CNT(a) == 0 ){
   1010             use_default_test = 1;
   1011         } else {
   1012             use_default_test = 0;
   1013         }
   1014     
   1015         parse_table_init(unit, &pt);
   1016     
   1017         parse_table_add(&pt, "DramNdx", PQ_STRING, (void *) (0),
   1018                 &(dram_ndx_srt), NULL);
   1019         parse_table_add(&pt, "WriteWeight", PQ_INT, (void *) 0,
   1020                 &(dt->run_info.write_weight), NULL);
   1021         parse_table_add(&pt, "ReadWeight", PQ_INT, (void*) 0,
   1022                 &(dt->run_info.read_weight), NULL);
   1023         parse_table_add(&pt, "BistNumActions", PQ_INT, (void *) 1,
   1024                 &(dt->run_info.bist_num_actions), NULL);
   1025         parse_table_add(&pt, "StartAddr", PQ_INT, (void *) 0,
   1026                 &(dt->run_info.bist_start_address), NULL);
   1027         parse_table_add(&pt, "EndAddr", PQ_INT, (void *) (0),
   1028                 &(dt->run_info.bist_end_address), NULL);
   1029         parse_table_add(&pt, "PatternMode", PQ_INT, (void *) (0),
   1030                 &(dt->run_info.pattern_mode), NULL);
   1031         parse_table_add(&pt, "Pattern0", PQ_INT, (void *) (0),
   1032                 &(dt->run_info.pattern[0]), NULL);
   1033         parse_table_add(&pt, "Pattern1", PQ_INT, (void *) (0),
   1034                 &(dt->run_info.pattern[1]), NULL);
   1035         parse_table_add(&pt, "Pattern2", PQ_INT, (void *) (0),
   1036                 &(dt->run_info.pattern[2]), NULL);
   1037         parse_table_add(&pt, "Pattern3", PQ_INT, (void *) (0),
   1038                 &(dt->run_info.pattern[3]), NULL);
   1039         parse_table_add(&pt, "Pattern4", PQ_INT, (void *) (0),
   1040                 &(dt->run_info.pattern[4]), NULL);
   1041         parse_table_add(&pt, "Pattern5", PQ_INT, (void *) (0),
   1042                 &(dt->run_info.pattern[5]), NULL);
   1043         parse_table_add(&pt, "Pattern6", PQ_INT, (void *) (0),
   1044                 &(dt->run_info.pattern[6]), NULL);
   1045         parse_table_add(&pt, "Pattern7", PQ_INT, (void *) (0),
   1046                 &(dt->run_info.pattern[7]), NULL);
   1047         parse_table_add(&pt, "ConsAddr8Banks", PQ_INT, (void *) (1),
   1048                 &cons_addr_8_banks, NULL);
   1049         parse_table_add(&pt, "AddressShiftMode", PQ_INT, (void *) (0),
   1050                 &address_shift_mode, NULL);
   1051         parse_table_add(&pt, "Infinite", PQ_INT, (void *) (0),
   1052                 &infinite, NULL);
   1053         parse_table_add(&pt, "AllAdress", PQ_INT, (void *) (0),
   1054                 &all_adress, NULL);
   1055         parse_table_add(&pt, "Stop", PQ_INT, (void *) (0),
   1056                 &stop, NULL);
   1057         parse_table_add(&pt, "GetData", PQ_INT, (void *) (0),
   1058                 &get_data, NULL);
   1059         parse_table_add(&pt, "TwoAddrMode", PQ_INT, (void *) (0),
   1060                 &two_addr_mode, NULL);
   1061     
   1062         if (parse_arg_eq(a, &pt) < 0) {
   1063             cli_out("%s: Invalid option: %s\n",
   1064                     ARG_CMD(a), ARG_CUR(a));
   1065             goto done;
   1066         }
   1067     
   1068         if (ARG_CNT(a) != 0) {
   1069             cli_out("%s: extra options starting with \"%s\"\n",
   1070                     ARG_CMD(a), ARG_CUR(a));
   1071             goto done;
   1072         }
   1073     
   1074         if( use_default_test != 0) {
   1075             all_adress = 1;
   1076         }
   1077     
   1078         dt->unit = unit;
   1079         dt->run_info.ddr_bist_flags = 0;
   1080         if(cons_addr_8_banks) {
   1081             dt->run_info.ddr_bist_flags |= DDR_BIST_CONS_ADDR_8_BANKS;
   1082         }
   1083         if(address_shift_mode) {
   1084             dt->run_info.ddr_bist_flags |= DDR_BIST_ADDRESS_SHIFT_MODE;
   1085         }
   1086         if(infinite) {
   1087             dt->run_info.ddr_bist_flags |= DDR_BIST_INFINITE;
   1088         }
   1089         if(all_adress) {
   1090             dt->run_info.ddr_bist_flags |= DDR_BIST_ALL_ADDRESS;
   1091         }
   1092         if(stop) {
   1093             dt->run_info.ddr_bist_flags |= DDR_BIST_STOP;
   1094         }
   1095         if(get_data) {
   1096             dt->run_info.ddr_bist_flags |= DDR_BIST_GET_DATA;
   1097         }
   1098         if(two_addr_mode) {
   1099             dt->run_info.ddr_bist_flags |= DDR_BIST_TWO_ADDRESS_MODE;
   1100         }
   1101     
   1102 
   1103         if (*dram_ndx_srt == '\0') {
   1104             /* Test all memories by default */
   1105             BCM_PBMP_CLEAR(dt->dram_ndx);
   1106             for (i = 0; i < SOC_DDR3_NUM_MEMORIES(unit); i++) {
   1107                 BCM_PBMP_PORT_ADD(dt->dram_ndx, i);
   1108             }
   1109         } else if (parse_small_integers(unit, dram_ndx_srt, &dt->dram_ndx) < 0) {
   1110             test_error(unit, "DramNdx parameter was not enter correctly\n");
   1111             return -1;
   1112         } 
   1113         
   1114         *p = dt;
   1115         rv = 0;
   1116     
   1117         done:
   1118            parse_arg_eq_done(&pt);
   1119            return rv;
   1120 }
   1121 
   1122 
   1123 int
   1124 ddr_bist_test_done(int unit, void *p)
   1125 {
   1126 #ifdef BCM_PETRA_SUPPORT
   1127     if (SOC_IS_ARAD(unit) || SOC_IS_DPP_DRC_COMBO28(unit)) {
   1128         return arad_bist_test_done(unit, p);
   1129     }
   1130 #endif
   1131 
   1132     LOG_INFO(BSL_LS_APPL_TESTS,
   1133              (BSL_META_U(unit,
   1134                          "DDR Bist Tests Done\n")));
   1135     sal_free(ddr_test_params[unit]);
   1136     ddr_test_params[unit] = NULL;
   1137     return BCM_E_NONE;
   1138 }
   1139 
   1140 #define KT2_DDR_DATA_WIDTH         16
   1141 #define KT2_BIST_BITS_PER_ADDR     256
   1142 
   1143 int ddr_bist_test(int unit, args_t *a, void *p)
   1144 {
   1145 #if defined(BCM_KATANA2_SUPPORT)
   1146     ddr_test_params_t *dt = p;
   1147     uint32 i, ci;
   1148     uint32 reg_val, bist_err_occured, bist_full_err_cnt, bist_single_err_cnt, bist_global_err_cnt;
   1149     uint32 max_bist_end_addr=0;
   1150     uint32 max_bist_start_addr=0;
   1151     uint32 uFailedData[8] = {0};
   1152     uint32 uFailedAddr = 0;
   1153     soc_pbmp_t valid_dram_pbmp;
   1154 #endif
   1155 
   1156 #ifdef BCM_PETRA_SUPPORT
   1157     if (SOC_IS_ARAD(unit) || SOC_IS_DPP_DRC_COMBO28(unit)) {
   1158         return arad_bist_test(unit, a, p);
   1159     }
   1160 #endif
   1161 
   1162 #if defined(BCM_KATANA2_SUPPORT)
   1163     if (SOC_IS_KATANA2(unit) ) {
   1164         max_bist_end_addr = (1 << soc_reg_field_length(unit, 
   1165                                   BISTENDADDRESSr, BISTENDADDRESSf)) - 1;
   1166         max_bist_start_addr = (1 << soc_reg_field_length(unit, 
   1167                                     BISTSTARTADDRESSr, BISTSTARTADDRESSf)) - 1;
   1168 
   1169         BCM_PBMP_CLEAR(valid_dram_pbmp);
   1170         for (i = 0; i < SOC_DDR3_NUM_MEMORIES(unit); i++) {
   1171             BCM_PBMP_PORT_ADD(valid_dram_pbmp, i);
   1172         }
   1173 
   1174         SOC_PBMP_ITER(dt->dram_ndx, ci) {
   1175 
   1176             if (!SOC_PBMP_MEMBER(valid_dram_pbmp, ci))  {
   1177                 continue;
   1178             }
   1179 
   1180             LOG_WARN(BSL_LS_APPL_TESTS,
   1181                   (BSL_META_U(unit, "Testing DRAM %d\n"), ci));
   1182 
   1183             if (dt->run_info.ddr_bist_flags & DDR_BIST_ALL_ADDRESS) {
   1184                 /* Remove all other flags */
   1185                 dt->run_info.ddr_bist_flags = DDR_BIST_ALL_ADDRESS;
   1186                 dt->run_info.bist_start_address = 0x0;
   1187                 dt->run_info.bist_end_address =  SOC_DDR3_NUM_COLUMNS(unit) *
   1188                                                  SOC_DDR3_NUM_ROWS(unit) *
   1189                                                  SOC_DDR3_NUM_BANKS(unit) *
   1190                                                  KT2_DDR_DATA_WIDTH /
   1191                                                  KT2_BIST_BITS_PER_ADDR - 1;
   1192                 if (dt->run_info.bist_end_address > max_bist_end_addr ) {
   1193                     LOG_ERROR(BSL_LS_APPL_TESTS,
   1194                               (BSL_META_U(unit,
   1195                                           "bist_end_address:%x exceeded max bist addr:%x"
   1196                                           " so Resetting to max \n"),
   1197                                dt->run_info.bist_end_address, max_bist_end_addr));
   1198                     dt->run_info.bist_end_address = max_bist_end_addr;
   1199                 } 
   1200                 dt->run_info.bist_num_actions =  dt->run_info.bist_end_address + 1;
   1201 
   1202                 dt->run_info.write_weight = 1;
   1203                 dt->run_info.read_weight = 0;
   1204                 dt->run_info.pattern_mode = DRAM_BIST_DATA_PATTERN_ADDR_MODE;
   1205 
   1206                if (_ddr_bist_test_start(dt->unit, ci, &(dt->run_info)) < 0) {
   1207                     cli_out("Error: First _ddr_bist_test_start () "
   1208                             "Failed:\n");
   1209                     return BCM_E_FAIL;
   1210                 }
   1211                 
   1212                 dt->run_info.write_weight = 0;
   1213                 dt->run_info.read_weight = 1;
   1214                 if (_ddr_bist_test_start(dt->unit, ci, &(dt->run_info)) < 0) {
   1215                      cli_out("Error: Second _ddr_bist_test_start () "
   1216                              "Failed:\n");
   1217                      return BCM_E_FAIL;
   1218                  }
   1219             } else { /* All Address */
   1220                 if (dt->run_info.bist_end_address > max_bist_end_addr ) {
   1221                     LOG_ERROR(BSL_LS_APPL_TESTS,
   1222                               (BSL_META_U(dt->unit,
   1223                                           "bist_end_address:%x exceeded max bist addr:%x"
   1224                                           " so Resetting to max \n"),
   1225                                dt->run_info.bist_end_address, max_bist_end_addr));
   1226                     dt->run_info.bist_end_address = max_bist_end_addr;
   1227                 } 
   1228                 if (dt->run_info.bist_start_address > max_bist_start_addr ) {
   1229                     LOG_ERROR(BSL_LS_APPL_TESTS,
   1230                               (BSL_META_U(dt->unit,
   1231                                           "bist_start_address:%x exceeded max bist addr:%x"
   1232                                           " so Resetting to max - 1 \n"),
   1233                                dt->run_info.bist_start_address, 
   1234                                max_bist_end_addr));
   1235                     dt->run_info.bist_end_address = max_bist_start_addr - 1;
   1236                 } 
   1237                 if (_ddr_bist_test_start(dt->unit, ci, &(dt->run_info)) < 0) {
   1238                      cli_out("Error: Second _ddr_bist_test_start () "
   1239                              "Failed:\n");
   1240                      return BCM_E_FAIL;
   1241                  }
   1242             }
   1243 #if defined(BCM_SABER2_SUPPORT)      
   1244             if (SOC_IS_SABER2(unit)) {
   1245                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit,
   1246                             BISTERROROCCURREDr, ci, 0, &bist_err_occured));
   1247 
   1248                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit,
   1249                             BISTFULLMASKERRORCOUNTERr, ci, 0,
   1250                             &bist_full_err_cnt));
   1251 
   1252                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit,
   1253                             BISTSINGLEBITMASKERRORCOUNTERr, ci, 0,
   1254                             &bist_single_err_cnt));
   1255 
   1256                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit,
   1257                             BISTGLOBALERRORCOUNTERr, ci, 0,
   1258                             &bist_global_err_cnt));
   1259  
   1260             } else 
   1261 #endif            
   1262             {
   1263                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTERROROCCURREDr, ci, 0, &reg_val));
   1264                 bist_err_occured = soc_reg_field_get(unit, BISTERROROCCURREDr, reg_val, ERROCCURREDf);
   1265 
   1266                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTFULLMASKERRORCOUNTERr, ci, 0, &reg_val));
   1267                 bist_full_err_cnt = soc_reg_field_get(unit, BISTFULLMASKERRORCOUNTERr, reg_val, FULLERRCNTf);
   1268 
   1269                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTSINGLEBITMASKERRORCOUNTERr, ci, 0, &reg_val));
   1270                 bist_single_err_cnt = soc_reg_field_get(unit, BISTSINGLEBITMASKERRORCOUNTERr, reg_val, SINGLEERRCNTf);
   1271                  
   1272                  SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTGLOBALERRORCOUNTERr, ci, 0, &reg_val));
   1273                 bist_global_err_cnt = soc_reg_field_get(unit, BISTGLOBALERRORCOUNTERr, reg_val, GLOBALERRCNTf); 
   1274             }
   1275 
   1276             if ((bist_err_occured != 0x0)  || (bist_full_err_cnt != 0x0)  || (bist_single_err_cnt != 0x0)  || (bist_global_err_cnt != 0x0)){
   1277                 cli_out("\nCI: %d \nResults:\n", ci);
   1278                 cli_out("Number of errors occured: 0x%x\n",
   1279                         bist_err_occured);
   1280                 cli_out("Number of full errors: %d\n", bist_full_err_cnt);
   1281                 cli_out("Number of single errors: %d\n",
   1282                         bist_single_err_cnt);
   1283                 cli_out("Number of global errors: %d\n",
   1284                         bist_global_err_cnt);
   1285 
   1286                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTADDRERRr,
   1287                                                       ci, 0, &uFailedAddr));
   1288                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD0r,
   1289                                                    ci, 0, &uFailedData[0]));
   1290                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD1r,
   1291                                                    ci, 0, &uFailedData[1]));
   1292                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD2r,
   1293                                                    ci, 0, &uFailedData[2]));
   1294                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD3r,
   1295                                                    ci, 0, &uFailedData[3]));
   1296                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD4r,
   1297                                                    ci, 0, &uFailedData[4]));
   1298                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD5r,
   1299                                                    ci, 0, &uFailedData[5]));
   1300                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD6r,
   1301                                                    ci, 0, &uFailedData[6]));
   1302                 SOC_IF_ERROR_RETURN(soc_reg32_get(unit, BISTLASTDATAERRWORD7r,
   1303                                                    ci, 0, &uFailedData[7]));
   1304 
   1305                 cli_out("CI%d Last Failing address = (0x%08x)\n",ci,
   1306                                                           uFailedAddr);
   1307                 for (i = 0; i < 8; i++) {
   1308                     if ( i == 4) {
   1309                         cli_out("\n");
   1310                     }
   1311                     cli_out("failing_data_%d = (0x%08x)  ", i,
   1312                                                     uFailedData[i]);
   1313                 }
   1314                 cli_out("\n");
   1315 
   1316                 return BCM_E_FAIL;
   1317             }
   1318         }
   1319         return BCM_E_NONE;
   1320     } else
   1321 #endif /* BCM_KATANA2_SUPPORT */
   1322 #if defined(BCM_HELIX5_SUPPORT)
   1323     if (SOC_IS_HELIX5(unit) ) {
   1324         uint32 FailedAddr = 0;
   1325         ydc_ddr_bist_info_t bist_info;
   1326         ydc_ddr_bist_err_cnt_t error_count;
   1327         LOG_WARN(BSL_LS_APPL_TESTS,
   1328                 (BSL_META_U(unit, "Testing DRAM\n")));
   1329 
   1330         SOC_IF_ERROR_RETURN(soc_iproc_ddr_init(unit));
   1331 
   1332         bist_info.write_weight = 255;
   1333         bist_info.read_weight = 255;
   1334         bist_info.bist_timer_us = 0;
   1335         bist_info.bist_num_actions = 51510;
   1336         bist_info.bist_start_address = 0x00000000;
   1337         bist_info.bist_end_address = 0x0FFFFFFF;
   1338         bist_info.mpr_mode = 0;
   1339         bist_info.prbs_mode = 1;
   1340         bist_info.addr_prbs_mode = 0;
   1341 
   1342         SOC_IF_ERROR_RETURN(soc_ydc_ddr_bist_config_set(unit, 0, &bist_info));
   1343 
   1344         SOC_IF_ERROR_RETURN(soc_ydc_ddr_bist_run(unit, 0, &error_count));
   1345 
   1346         if ((error_count.bist_err_occur != 0x0)  || (error_count.bist_full_err_cnt != 0x0) ||
   1347             (error_count.bist_single_err_cnt != 0x0) || (error_count.bist_global_err_cnt != 0x0)) {
   1348                 cli_out("\nResults:\n");
   1349                 cli_out("Number of errors occurred: 0x%x\n",
   1350                         error_count.bist_err_occur);
   1351                 cli_out("Number of full errors: %d\n", error_count.bist_full_err_cnt);
   1352                 cli_out("Number of single errors: %d\n",
   1353                         error_count.bist_single_err_cnt);
   1354                 cli_out("Number of global errors: %d\n",
   1355                         error_count.bist_global_err_cnt);
   1356 
   1357                 SOC_IF_ERROR_RETURN(READ_DDR_BISTLASTADDRERRr(unit,&FailedAddr));
   1358                 cli_out("Last Failing address = (0x%08x)\n", FailedAddr);
   1359                 cli_out("\n");
   1360 
   1361                 return BCM_E_FAIL;
   1362         }
   1363         return BCM_E_NONE;
   1364     } else
   1365 #endif /* BCM_HELIX5_SUPPORT */
   1366     {
   1367         return BCM_E_UNAVAIL;
   1368     }
   1369 }
   1370 
   1371 #endif /* defined(BCM_DDR3_SUPPORT) || defined(BCM_PETRA_SUPPORT) */