|
@@ -1,5 +1,5 @@
|
|
/*
|
|
/*
|
|
- * Copyright 2008-2011 Freescale Semiconductor, Inc.
|
|
|
|
|
|
+ * Copyright 2008-2012 Freescale Semiconductor, Inc.
|
|
*
|
|
*
|
|
* This program is free software; you can redistribute it and/or
|
|
* This program is free software; you can redistribute it and/or
|
|
* modify it under the terms of the GNU General Public License
|
|
* modify it under the terms of the GNU General Public License
|
|
@@ -15,13 +15,15 @@
|
|
#include <common.h>
|
|
#include <common.h>
|
|
#include <i2c.h>
|
|
#include <i2c.h>
|
|
#include <asm/fsl_ddr_sdram.h>
|
|
#include <asm/fsl_ddr_sdram.h>
|
|
|
|
+#include <asm/fsl_law.h>
|
|
|
|
|
|
#include "ddr.h"
|
|
#include "ddr.h"
|
|
|
|
|
|
-extern void fsl_ddr_set_lawbar(
|
|
|
|
|
|
+void fsl_ddr_set_lawbar(
|
|
const common_timing_params_t *memctl_common_params,
|
|
const common_timing_params_t *memctl_common_params,
|
|
unsigned int memctl_interleaved,
|
|
unsigned int memctl_interleaved,
|
|
unsigned int ctrl_num);
|
|
unsigned int ctrl_num);
|
|
|
|
+void fsl_ddr_set_intl3r(const unsigned int granule_size);
|
|
|
|
|
|
/* processor specific function */
|
|
/* processor specific function */
|
|
extern void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs,
|
|
extern void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs,
|
|
@@ -51,6 +53,22 @@ u8 spd_i2c_addr[CONFIG_NUM_DDR_CONTROLLERS][CONFIG_DIMM_SLOTS_PER_CTLR] = {
|
|
[1][0] = SPD_EEPROM_ADDRESS3, /* controller 2 */
|
|
[1][0] = SPD_EEPROM_ADDRESS3, /* controller 2 */
|
|
[1][1] = SPD_EEPROM_ADDRESS4, /* controller 2 */
|
|
[1][1] = SPD_EEPROM_ADDRESS4, /* controller 2 */
|
|
};
|
|
};
|
|
|
|
+#elif (CONFIG_NUM_DDR_CONTROLLERS == 3) && (CONFIG_DIMM_SLOTS_PER_CTLR == 1)
|
|
|
|
+u8 spd_i2c_addr[CONFIG_NUM_DDR_CONTROLLERS][CONFIG_DIMM_SLOTS_PER_CTLR] = {
|
|
|
|
+ [0][0] = SPD_EEPROM_ADDRESS1, /* controller 1 */
|
|
|
|
+ [1][0] = SPD_EEPROM_ADDRESS2, /* controller 2 */
|
|
|
|
+ [2][0] = SPD_EEPROM_ADDRESS3, /* controller 3 */
|
|
|
|
+};
|
|
|
|
+#elif (CONFIG_NUM_DDR_CONTROLLERS == 3) && (CONFIG_DIMM_SLOTS_PER_CTLR == 2)
|
|
|
|
+u8 spd_i2c_addr[CONFIG_NUM_DDR_CONTROLLERS][CONFIG_DIMM_SLOTS_PER_CTLR] = {
|
|
|
|
+ [0][0] = SPD_EEPROM_ADDRESS1, /* controller 1 */
|
|
|
|
+ [0][1] = SPD_EEPROM_ADDRESS2, /* controller 1 */
|
|
|
|
+ [1][0] = SPD_EEPROM_ADDRESS3, /* controller 2 */
|
|
|
|
+ [1][1] = SPD_EEPROM_ADDRESS4, /* controller 2 */
|
|
|
|
+ [2][0] = SPD_EEPROM_ADDRESS5, /* controller 3 */
|
|
|
|
+ [2][1] = SPD_EEPROM_ADDRESS6, /* controller 3 */
|
|
|
|
+};
|
|
|
|
+
|
|
#endif
|
|
#endif
|
|
|
|
|
|
static void __get_spd(generic_spd_eeprom_t *spd, u8 i2c_address)
|
|
static void __get_spd(generic_spd_eeprom_t *spd, u8 i2c_address)
|
|
@@ -156,12 +174,12 @@ const char * step_to_string(unsigned int step) {
|
|
return step_string_tbl[s];
|
|
return step_string_tbl[s];
|
|
}
|
|
}
|
|
|
|
|
|
-int step_assign_addresses(fsl_ddr_info_t *pinfo,
|
|
|
|
- unsigned int dbw_cap_adj[],
|
|
|
|
- unsigned int *all_memctl_interleaving,
|
|
|
|
- unsigned int *all_ctlr_rank_interleaving)
|
|
|
|
|
|
+unsigned long long step_assign_addresses(fsl_ddr_info_t *pinfo,
|
|
|
|
+ unsigned int dbw_cap_adj[])
|
|
{
|
|
{
|
|
int i, j;
|
|
int i, j;
|
|
|
|
+ unsigned long long total_mem, current_mem_base, total_ctlr_mem;
|
|
|
|
+ unsigned long long rank_density, ctlr_density = 0;
|
|
|
|
|
|
/*
|
|
/*
|
|
* If a reduced data width is requested, but the SPD
|
|
* If a reduced data width is requested, but the SPD
|
|
@@ -220,86 +238,108 @@ int step_assign_addresses(fsl_ddr_info_t *pinfo,
|
|
"specified controller %u\n", i);
|
|
"specified controller %u\n", i);
|
|
return 1;
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
+ debug("dbw_cap_adj[%d]=%d\n", i, dbw_cap_adj[i]);
|
|
}
|
|
}
|
|
|
|
|
|
- j = 0;
|
|
|
|
- for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++)
|
|
|
|
- if (pinfo->memctl_opts[i].memctl_interleaving)
|
|
|
|
- j++;
|
|
|
|
- /*
|
|
|
|
- * Not support less than all memory controllers interleaving
|
|
|
|
- * if more than two controllers
|
|
|
|
- */
|
|
|
|
- if (j == CONFIG_NUM_DDR_CONTROLLERS)
|
|
|
|
- *all_memctl_interleaving = 1;
|
|
|
|
-
|
|
|
|
- /* Check that all controllers are rank interleaving. */
|
|
|
|
- j = 0;
|
|
|
|
- for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++)
|
|
|
|
- if (pinfo->memctl_opts[i].ba_intlv_ctl)
|
|
|
|
- j++;
|
|
|
|
- /*
|
|
|
|
- * All memory controllers must be populated to qualify for
|
|
|
|
- * all controller rank interleaving
|
|
|
|
- */
|
|
|
|
- if (j == CONFIG_NUM_DDR_CONTROLLERS)
|
|
|
|
- *all_ctlr_rank_interleaving = 1;
|
|
|
|
-
|
|
|
|
- if (*all_memctl_interleaving) {
|
|
|
|
- unsigned long long addr, total_mem_per_ctlr = 0;
|
|
|
|
- /*
|
|
|
|
- * If interleaving between memory controllers,
|
|
|
|
- * make each controller start at a base address
|
|
|
|
- * of 0.
|
|
|
|
- *
|
|
|
|
- * Also, if bank interleaving (chip select
|
|
|
|
- * interleaving) is enabled on each memory
|
|
|
|
- * controller, CS0 needs to be programmed to
|
|
|
|
- * cover the entire memory range on that memory
|
|
|
|
- * controller
|
|
|
|
- *
|
|
|
|
- * Bank interleaving also implies that each
|
|
|
|
- * addressed chip select is identical in size.
|
|
|
|
- */
|
|
|
|
-
|
|
|
|
|
|
+ current_mem_base = 0ull;
|
|
|
|
+ total_mem = 0;
|
|
|
|
+ if (pinfo->memctl_opts[0].memctl_interleaving) {
|
|
|
|
+ rank_density = pinfo->dimm_params[0][0].rank_density >>
|
|
|
|
+ dbw_cap_adj[0];
|
|
|
|
+ switch (pinfo->memctl_opts[0].ba_intlv_ctl &
|
|
|
|
+ FSL_DDR_CS0_CS1_CS2_CS3) {
|
|
|
|
+ case FSL_DDR_CS0_CS1_CS2_CS3:
|
|
|
|
+ ctlr_density = 4 * rank_density;
|
|
|
|
+ break;
|
|
|
|
+ case FSL_DDR_CS0_CS1:
|
|
|
|
+ case FSL_DDR_CS0_CS1_AND_CS2_CS3:
|
|
|
|
+ ctlr_density = 2 * rank_density;
|
|
|
|
+ break;
|
|
|
|
+ case FSL_DDR_CS2_CS3:
|
|
|
|
+ default:
|
|
|
|
+ ctlr_density = rank_density;
|
|
|
|
+ break;
|
|
|
|
+ }
|
|
|
|
+ debug("rank density is 0x%llx, ctlr density is 0x%llx\n",
|
|
|
|
+ rank_density, ctlr_density);
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
- addr = 0;
|
|
|
|
- pinfo->common_timing_params[i].base_address = 0ull;
|
|
|
|
- for (j = 0; j < CONFIG_DIMM_SLOTS_PER_CTLR; j++) {
|
|
|
|
- unsigned long long cap
|
|
|
|
- = pinfo->dimm_params[i][j].capacity;
|
|
|
|
-
|
|
|
|
- pinfo->dimm_params[i][j].base_address = addr;
|
|
|
|
- addr += cap >> dbw_cap_adj[i];
|
|
|
|
- total_mem_per_ctlr += cap >> dbw_cap_adj[i];
|
|
|
|
|
|
+ if (pinfo->memctl_opts[i].memctl_interleaving) {
|
|
|
|
+ switch (pinfo->memctl_opts[i].memctl_interleaving_mode) {
|
|
|
|
+ case FSL_DDR_CACHE_LINE_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_PAGE_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_BANK_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_SUPERBANK_INTERLEAVING:
|
|
|
|
+ total_ctlr_mem = 2 * ctlr_density;
|
|
|
|
+ break;
|
|
|
|
+ case FSL_DDR_3WAY_1KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_3WAY_4KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_3WAY_8KB_INTERLEAVING:
|
|
|
|
+ total_ctlr_mem = 3 * ctlr_density;
|
|
|
|
+ break;
|
|
|
|
+ case FSL_DDR_4WAY_1KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_4WAY_4KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_4WAY_8KB_INTERLEAVING:
|
|
|
|
+ total_ctlr_mem = 4 * ctlr_density;
|
|
|
|
+ break;
|
|
|
|
+ default:
|
|
|
|
+ panic("Unknown interleaving mode");
|
|
|
|
+ }
|
|
|
|
+ pinfo->common_timing_params[i].base_address =
|
|
|
|
+ current_mem_base;
|
|
|
|
+ pinfo->common_timing_params[i].total_mem =
|
|
|
|
+ total_ctlr_mem;
|
|
|
|
+ total_mem = current_mem_base + total_ctlr_mem;
|
|
|
|
+ debug("ctrl %d base 0x%llx\n", i, current_mem_base);
|
|
|
|
+ debug("ctrl %d total 0x%llx\n", i, total_ctlr_mem);
|
|
|
|
+ } else {
|
|
|
|
+ /* when 3rd controller not interleaved */
|
|
|
|
+ current_mem_base = total_mem;
|
|
|
|
+ total_ctlr_mem = 0;
|
|
|
|
+ pinfo->common_timing_params[i].base_address =
|
|
|
|
+ current_mem_base;
|
|
|
|
+ for (j = 0; j < CONFIG_DIMM_SLOTS_PER_CTLR; j++) {
|
|
|
|
+ unsigned long long cap =
|
|
|
|
+ pinfo->dimm_params[i][j].capacity >> dbw_cap_adj[i];
|
|
|
|
+ pinfo->dimm_params[i][j].base_address =
|
|
|
|
+ current_mem_base;
|
|
|
|
+ debug("ctrl %d dimm %d base 0x%llx\n", i, j, current_mem_base);
|
|
|
|
+ current_mem_base += cap;
|
|
|
|
+ total_ctlr_mem += cap;
|
|
|
|
+ }
|
|
|
|
+ debug("ctrl %d total 0x%llx\n", i, total_ctlr_mem);
|
|
|
|
+ pinfo->common_timing_params[i].total_mem =
|
|
|
|
+ total_ctlr_mem;
|
|
|
|
+ total_mem += total_ctlr_mem;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
- pinfo->common_timing_params[0].total_mem = total_mem_per_ctlr;
|
|
|
|
} else {
|
|
} else {
|
|
/*
|
|
/*
|
|
* Simple linear assignment if memory
|
|
* Simple linear assignment if memory
|
|
* controllers are not interleaved.
|
|
* controllers are not interleaved.
|
|
*/
|
|
*/
|
|
- unsigned long long cur_memsize = 0;
|
|
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
- u64 total_mem_per_ctlr = 0;
|
|
|
|
|
|
+ total_ctlr_mem = 0;
|
|
pinfo->common_timing_params[i].base_address =
|
|
pinfo->common_timing_params[i].base_address =
|
|
- cur_memsize;
|
|
|
|
|
|
+ current_mem_base;
|
|
for (j = 0; j < CONFIG_DIMM_SLOTS_PER_CTLR; j++) {
|
|
for (j = 0; j < CONFIG_DIMM_SLOTS_PER_CTLR; j++) {
|
|
/* Compute DIMM base addresses. */
|
|
/* Compute DIMM base addresses. */
|
|
unsigned long long cap =
|
|
unsigned long long cap =
|
|
- pinfo->dimm_params[i][j].capacity;
|
|
|
|
|
|
+ pinfo->dimm_params[i][j].capacity >> dbw_cap_adj[i];
|
|
pinfo->dimm_params[i][j].base_address =
|
|
pinfo->dimm_params[i][j].base_address =
|
|
- cur_memsize;
|
|
|
|
- cur_memsize += cap >> dbw_cap_adj[i];
|
|
|
|
- total_mem_per_ctlr += cap >> dbw_cap_adj[i];
|
|
|
|
|
|
+ current_mem_base;
|
|
|
|
+ debug("ctrl %d dimm %d base 0x%llx\n", i, j, current_mem_base);
|
|
|
|
+ current_mem_base += cap;
|
|
|
|
+ total_ctlr_mem += cap;
|
|
}
|
|
}
|
|
|
|
+ debug("ctrl %d total 0x%llx\n", i, total_ctlr_mem);
|
|
pinfo->common_timing_params[i].total_mem =
|
|
pinfo->common_timing_params[i].total_mem =
|
|
- total_mem_per_ctlr;
|
|
|
|
|
|
+ total_ctlr_mem;
|
|
|
|
+ total_mem += total_ctlr_mem;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
+ debug("Total mem by %s is 0x%llx\n", __func__, total_mem);
|
|
|
|
|
|
- return 0;
|
|
|
|
|
|
+ return total_mem;
|
|
}
|
|
}
|
|
|
|
|
|
unsigned long long
|
|
unsigned long long
|
|
@@ -307,8 +347,6 @@ fsl_ddr_compute(fsl_ddr_info_t *pinfo, unsigned int start_step,
|
|
unsigned int size_only)
|
|
unsigned int size_only)
|
|
{
|
|
{
|
|
unsigned int i, j;
|
|
unsigned int i, j;
|
|
- unsigned int all_controllers_memctl_interleaving = 0;
|
|
|
|
- unsigned int all_controllers_rank_interleaving = 0;
|
|
|
|
unsigned long long total_mem = 0;
|
|
unsigned long long total_mem = 0;
|
|
|
|
|
|
fsl_ddr_cfg_regs_t *ddr_reg = pinfo->fsl_ddr_config_reg;
|
|
fsl_ddr_cfg_regs_t *ddr_reg = pinfo->fsl_ddr_config_reg;
|
|
@@ -346,8 +384,9 @@ fsl_ddr_compute(fsl_ddr_info_t *pinfo, unsigned int start_step,
|
|
retval = compute_dimm_parameters(spd, pdimm, i);
|
|
retval = compute_dimm_parameters(spd, pdimm, i);
|
|
#ifdef CONFIG_SYS_DDR_RAW_TIMING
|
|
#ifdef CONFIG_SYS_DDR_RAW_TIMING
|
|
if (retval != 0) {
|
|
if (retval != 0) {
|
|
- printf("SPD error! Trying fallback to "
|
|
|
|
- "raw timing calculation\n");
|
|
|
|
|
|
+ printf("SPD error on controller %d! "
|
|
|
|
+ "Trying fallback to raw timing "
|
|
|
|
+ "calculation\n", i);
|
|
fsl_ddr_get_dimm_params(pdimm, i, j);
|
|
fsl_ddr_get_dimm_params(pdimm, i, j);
|
|
}
|
|
}
|
|
#else
|
|
#else
|
|
@@ -407,17 +446,14 @@ fsl_ddr_compute(fsl_ddr_info_t *pinfo, unsigned int start_step,
|
|
&pinfo->memctl_opts[i],
|
|
&pinfo->memctl_opts[i],
|
|
pinfo->dimm_params[i], i);
|
|
pinfo->dimm_params[i], i);
|
|
}
|
|
}
|
|
- check_interleaving_options(pinfo);
|
|
|
|
case STEP_ASSIGN_ADDRESSES:
|
|
case STEP_ASSIGN_ADDRESSES:
|
|
/* STEP 5: Assign addresses to chip selects */
|
|
/* STEP 5: Assign addresses to chip selects */
|
|
- step_assign_addresses(pinfo,
|
|
|
|
- dbw_capacity_adjust,
|
|
|
|
- &all_controllers_memctl_interleaving,
|
|
|
|
- &all_controllers_rank_interleaving);
|
|
|
|
|
|
+ check_interleaving_options(pinfo);
|
|
|
|
+ total_mem = step_assign_addresses(pinfo, dbw_capacity_adjust);
|
|
|
|
|
|
case STEP_COMPUTE_REGS:
|
|
case STEP_COMPUTE_REGS:
|
|
/* STEP 6: compute controller register values */
|
|
/* STEP 6: compute controller register values */
|
|
- debug("FSL Memory ctrl cg register computation\n");
|
|
|
|
|
|
+ debug("FSL Memory ctrl register computation\n");
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
if (timing_params[i].ndimms_present == 0) {
|
|
if (timing_params[i].ndimms_present == 0) {
|
|
memset(&ddr_reg[i], 0,
|
|
memset(&ddr_reg[i], 0,
|
|
@@ -437,21 +473,7 @@ fsl_ddr_compute(fsl_ddr_info_t *pinfo, unsigned int start_step,
|
|
break;
|
|
break;
|
|
}
|
|
}
|
|
|
|
|
|
- /* Compute the total amount of memory. */
|
|
|
|
-
|
|
|
|
- /*
|
|
|
|
- * If bank interleaving but NOT memory controller interleaving
|
|
|
|
- * CS_BNDS describe the quantity of memory on each memory
|
|
|
|
- * controller, so the total is the sum across.
|
|
|
|
- */
|
|
|
|
- if (!all_controllers_memctl_interleaving
|
|
|
|
- && all_controllers_rank_interleaving) {
|
|
|
|
- total_mem = 0;
|
|
|
|
- for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
|
|
- total_mem += timing_params[i].total_mem;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- } else {
|
|
|
|
|
|
+ {
|
|
/*
|
|
/*
|
|
* Compute the amount of memory available just by
|
|
* Compute the amount of memory available just by
|
|
* looking for the highest valid CSn_BNDS value.
|
|
* looking for the highest valid CSn_BNDS value.
|
|
@@ -489,7 +511,7 @@ fsl_ddr_compute(fsl_ddr_info_t *pinfo, unsigned int start_step,
|
|
phys_size_t fsl_ddr_sdram(void)
|
|
phys_size_t fsl_ddr_sdram(void)
|
|
{
|
|
{
|
|
unsigned int i;
|
|
unsigned int i;
|
|
- unsigned int memctl_interleaved;
|
|
|
|
|
|
+ unsigned int law_memctl = LAW_TRGT_IF_DDR_1;
|
|
unsigned long long total_memory;
|
|
unsigned long long total_memory;
|
|
fsl_ddr_info_t info;
|
|
fsl_ddr_info_t info;
|
|
|
|
|
|
@@ -504,34 +526,6 @@ phys_size_t fsl_ddr_sdram(void)
|
|
#endif
|
|
#endif
|
|
total_memory = fsl_ddr_compute(&info, STEP_GET_SPD, 0);
|
|
total_memory = fsl_ddr_compute(&info, STEP_GET_SPD, 0);
|
|
|
|
|
|
- /* Check for memory controller interleaving. */
|
|
|
|
- memctl_interleaved = 0;
|
|
|
|
- for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
|
|
- memctl_interleaved +=
|
|
|
|
- info.memctl_opts[i].memctl_interleaving;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- if (memctl_interleaved) {
|
|
|
|
- if (memctl_interleaved == CONFIG_NUM_DDR_CONTROLLERS) {
|
|
|
|
- debug("memctl interleaving\n");
|
|
|
|
- /*
|
|
|
|
- * Change the meaning of memctl_interleaved
|
|
|
|
- * to be "boolean".
|
|
|
|
- */
|
|
|
|
- memctl_interleaved = 1;
|
|
|
|
- } else {
|
|
|
|
- printf("Warning: memctl interleaving not "
|
|
|
|
- "properly configured on all controllers\n");
|
|
|
|
- memctl_interleaved = 0;
|
|
|
|
- for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++)
|
|
|
|
- info.memctl_opts[i].memctl_interleaving = 0;
|
|
|
|
- debug("Recomputing with memctl_interleaving off.\n");
|
|
|
|
- total_memory = fsl_ddr_compute(&info,
|
|
|
|
- STEP_ASSIGN_ADDRESSES,
|
|
|
|
- 0);
|
|
|
|
- }
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
/* Program configuration registers. */
|
|
/* Program configuration registers. */
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
debug("Programming controller %u\n", i);
|
|
debug("Programming controller %u\n", i);
|
|
@@ -544,24 +538,69 @@ phys_size_t fsl_ddr_sdram(void)
|
|
fsl_ddr_set_memctl_regs(&(info.fsl_ddr_config_reg[i]), i);
|
|
fsl_ddr_set_memctl_regs(&(info.fsl_ddr_config_reg[i]), i);
|
|
}
|
|
}
|
|
|
|
|
|
- if (memctl_interleaved) {
|
|
|
|
- const unsigned int ctrl_num = 0;
|
|
|
|
-
|
|
|
|
- /* Only set LAWBAR1 if memory controller interleaving is on. */
|
|
|
|
- fsl_ddr_set_lawbar(&info.common_timing_params[0],
|
|
|
|
- memctl_interleaved, ctrl_num);
|
|
|
|
- } else {
|
|
|
|
- /*
|
|
|
|
- * Memory controller interleaving is NOT on;
|
|
|
|
- * set each lawbar individually.
|
|
|
|
- */
|
|
|
|
- for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
|
|
|
|
+ /* program LAWs */
|
|
|
|
+ for (i = 0; i < CONFIG_NUM_DDR_CONTROLLERS; i++) {
|
|
|
|
+ if (info.memctl_opts[i].memctl_interleaving) {
|
|
|
|
+ switch (info.memctl_opts[i].memctl_interleaving_mode) {
|
|
|
|
+ case FSL_DDR_CACHE_LINE_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_PAGE_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_BANK_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_SUPERBANK_INTERLEAVING:
|
|
|
|
+ if (i == 0) {
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_INTRLV;
|
|
|
|
+ fsl_ddr_set_lawbar(&info.common_timing_params[i],
|
|
|
|
+ law_memctl, i);
|
|
|
|
+ } else if (i == 2) {
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_INTLV_34;
|
|
|
|
+ fsl_ddr_set_lawbar(&info.common_timing_params[i],
|
|
|
|
+ law_memctl, i);
|
|
|
|
+ }
|
|
|
|
+ break;
|
|
|
|
+ case FSL_DDR_3WAY_1KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_3WAY_4KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_3WAY_8KB_INTERLEAVING:
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_INTLV_123;
|
|
|
|
+ if (i == 0) {
|
|
|
|
+ fsl_ddr_set_intl3r(info.memctl_opts[i].memctl_interleaving_mode);
|
|
|
|
+ fsl_ddr_set_lawbar(&info.common_timing_params[i],
|
|
|
|
+ law_memctl, i);
|
|
|
|
+ }
|
|
|
|
+ break;
|
|
|
|
+ case FSL_DDR_4WAY_1KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_4WAY_4KB_INTERLEAVING:
|
|
|
|
+ case FSL_DDR_4WAY_8KB_INTERLEAVING:
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_INTLV_1234;
|
|
|
|
+ if (i == 0)
|
|
|
|
+ fsl_ddr_set_lawbar(&info.common_timing_params[i],
|
|
|
|
+ law_memctl, i);
|
|
|
|
+ /* place holder for future 4-way interleaving */
|
|
|
|
+ break;
|
|
|
|
+ default:
|
|
|
|
+ break;
|
|
|
|
+ }
|
|
|
|
+ } else {
|
|
|
|
+ switch (i) {
|
|
|
|
+ case 0:
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_1;
|
|
|
|
+ break;
|
|
|
|
+ case 1:
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_2;
|
|
|
|
+ break;
|
|
|
|
+ case 2:
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_3;
|
|
|
|
+ break;
|
|
|
|
+ case 3:
|
|
|
|
+ law_memctl = LAW_TRGT_IF_DDR_4;
|
|
|
|
+ break;
|
|
|
|
+ default:
|
|
|
|
+ break;
|
|
|
|
+ }
|
|
fsl_ddr_set_lawbar(&info.common_timing_params[i],
|
|
fsl_ddr_set_lawbar(&info.common_timing_params[i],
|
|
- 0, i);
|
|
|
|
|
|
+ law_memctl, i);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
- debug("total_memory = %llu\n", total_memory);
|
|
|
|
|
|
+ debug("total_memory by %s = %llu\n", __func__, total_memory);
|
|
|
|
|
|
#if !defined(CONFIG_PHYS_64BIT)
|
|
#if !defined(CONFIG_PHYS_64BIT)
|
|
/* Check for 4G or more. Bad. */
|
|
/* Check for 4G or more. Bad. */
|