* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
-#include "amdk8_f.h"
-#include "spd_ddr2.h"
-
-#ifndef QRANK_DIMM_SUPPORT
-#define QRANK_DIMM_SUPPORT 0
-#endif
-
-#if CONFIG_USE_PRINTK_IN_CAR
-#else
-#error This file needs CONFIG_USE_PRINTK_IN_CAR
+#include "f.h"
+#include <spd_ddr2.h>
+#if CONFIG_HAVE_OPTION_TABLE
+#include "option_table.h"
-#define RAM_TIMING_DEBUG 0
-
-#if RAM_TIMING_DEBUG == 1
-#define printk_raminit printk_debug
+#if CONFIG_DEBUG_RAM_SETUP
+#define printk_raminit(args...) printk(BIOS_DEBUG, args)
/* for PCI_ADDR(0, 0x18, 2, 0x98) index,
/* for PCI_ADDR(0, 0x18, 2, 0x98) index,
* MEMCLK cycle
* 1 = One additional MEMCLK of setup time is provided on all
* DRAM address and control signals except CS, CKE, and ODT;
* MEMCLK cycle
* 1 = One additional MEMCLK of setup time is provided on all
* DRAM address and control signals except CS, CKE, and ODT;
reg |= register_values[i+2];
pci_write_config32(dev, where, reg);
}
reg |= register_values[i+2];
pci_write_config32(dev, where, reg);
}
static int is_dual_channel(const struct mem_controller *ctrl)
{
uint32_t dcl;
dcl = pci_read_config32(ctrl->f2, DRAM_CONFIG_LOW);
return dcl & DCL_Width128;
}
static int is_dual_channel(const struct mem_controller *ctrl)
{
uint32_t dcl;
dcl = pci_read_config32(ctrl->f2, DRAM_CONFIG_LOW);
return dcl & DCL_Width128;
}
- /* Test to see if I am an Opteron.
- * FIXME Testing dual channel capability is correct for now
- * but a better test is probably required.
- * m2 and s1g1 support dual channel too. but only support unbuffered dimm
+ /* Test to see if I am an Opteron. M2 and S1G1 support dual
+ * channel, too, but only support unbuffered DIMMs so we need a
+ * better test for Opterons.
+ * However, all code uses is_opteron() to find out whether to
+ * use dual channel, so if we really check for opteron here, we
+ * need to fix up all code using this function, too.
uint32_t nbcap;
nbcap = pci_read_config32(ctrl->f3, NORTHBRIDGE_CAP);
return !!(nbcap & NBCAP_128Bit);
}
uint32_t nbcap;
nbcap = pci_read_config32(ctrl->f3, NORTHBRIDGE_CAP);
return !!(nbcap & NBCAP_128Bit);
}
static int is_registered(const struct mem_controller *ctrl)
{
/* Test to see if we are dealing with registered SDRAM.
static int is_registered(const struct mem_controller *ctrl)
{
/* Test to see if we are dealing with registered SDRAM.
dcl = pci_read_config32(ctrl->f2, DRAM_CONFIG_LOW);
return !(dcl & DCL_UnBuffDimm);
}
dcl = pci_read_config32(ctrl->f2, DRAM_CONFIG_LOW);
return !(dcl & DCL_UnBuffDimm);
}
if (value <=4 ) value += 8; // add back to 1G to high
value += (27-5); // make 128MB to the real lines
if ( value != (sz->per_rank)) {
if (value <=4 ) value += 8; // add back to 1G to high
value += (27-5); // make 128MB to the real lines
if ( value != (sz->per_rank)) {
- struct dimm_size *sz, unsigned index, struct mem_info *meminfo)
+ struct dimm_size *sz, unsigned index,
+ struct mem_info *meminfo)
/* Set the appropriate DIMM base address register */
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 0) << 2), base0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 1) << 2), base1);
/* Set the appropriate DIMM base address register */
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 0) << 2), base0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 1) << 2), base1);
if (sz->rank == 4) {
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 4) << 2), base0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 5) << 2), base1);
if (sz->rank == 4) {
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 4) << 2), base0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 5) << 2), base1);
} else {
dword = pci_read_config32(ctrl->f2, DRAM_TIMING_LOW); //Channel A
dword &= ~(ClkDis0 >> index);
} else {
dword = pci_read_config32(ctrl->f2, DRAM_TIMING_LOW); //Channel A
dword &= ~(ClkDis0 >> index);
if (meminfo->is_Width128) { // ChannelA+B
dword = pci_read_config32(ctrl->f2, DRAM_CTRL_MISC);
dword &= ~(ClkDis0 >> index);
if (meminfo->is_Width128) { // ChannelA+B
dword = pci_read_config32(ctrl->f2, DRAM_CTRL_MISC);
dword &= ~(ClkDis0 >> index);
}
map = pci_read_config32(ctrl->f2, DRAM_BANK_ADDR_MAP);
map &= ~(0xf << (index * 4));
}
map = pci_read_config32(ctrl->f2, DRAM_BANK_ADDR_MAP);
map &= ~(0xf << (index * 4));
unsigned temp_map;
temp_map = cs_map_aaa[(sz->bank-2)*3*4 + (sz->rows - 13)*3 + (sz->col - 9) ];
map |= temp_map << (index*4);
unsigned temp_map;
temp_map = cs_map_aaa[(sz->bank-2)*3*4 + (sz->rows - 13)*3 + (sz->col - 9) ];
map |= temp_map << (index*4);
return -1; /* Report SPD error */
}
set_dimm_size(ctrl, sz, i, meminfo);
return -1; /* Report SPD error */
}
set_dimm_size(ctrl, sz, i, meminfo);
- set_dimm_cs_map (ctrl, sz, i, meminfo);
+ set_dimm_cs_map(ctrl, sz, i, meminfo);
static void set_top_mem(unsigned tom_k, unsigned hole_startk)
{
/* Error if I don't have memory */
static void set_top_mem(unsigned tom_k, unsigned hole_startk)
{
/* Error if I don't have memory */
}
/* Leave a 64M hole between TOP_MEM and TOP_MEM2
* so I can see my rom chip and other I/O devices.
*/
if (tom_k >= 0x003f0000) {
}
/* Leave a 64M hole between TOP_MEM and TOP_MEM2
* so I can see my rom chip and other I/O devices.
*/
if (tom_k >= 0x003f0000) {
/* Compute the initial values for csbase and csbask.
* In csbase just set the enable bit and the base to zero.
* In csmask set the mask bits for the size and page level interleave.
/* Compute the initial values for csbase and csbask.
* In csbase just set the enable bit and the base to zero.
* In csmask set the mask bits for the size and page level interleave.
static void order_dimms(const struct mem_controller *ctrl,
struct mem_info *meminfo)
{
unsigned long tom_k, base_k;
static void order_dimms(const struct mem_controller *ctrl,
struct mem_info *meminfo)
{
unsigned long tom_k, base_k;
- if (read_option(CMOS_VSTART_interleave_chip_selects,
- CMOS_VLEN_interleave_chip_selects, 1) != 0) {
- tom_k = interleave_chip_selects(ctrl, meminfo->is_Width128);
- } else {
- printk_debug("Interleaving disabled\n");
- tom_k = 0;
- }
-
+ tom_k = interleave_chip_selects(ctrl, meminfo->is_Width128);
+
/* Compute the memory base address */
base_k = memory_end_k(ctrl, ctrl->node_id);
tom_k += base_k;
/* Compute the memory base address */
base_k = memory_end_k(ctrl, ctrl->node_id);
tom_k += base_k;
static long disable_dimm(const struct mem_controller *ctrl, unsigned index,
struct mem_info *meminfo)
{
static long disable_dimm(const struct mem_controller *ctrl, unsigned index,
struct mem_info *meminfo)
{
if (!(meminfo->dimm_mask & 0x0F) && (meminfo->dimm_mask & 0xF0)) { /* channelB only? */
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 4) << 2), 0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 5) << 2), 0);
} else {
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 0) << 2), 0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 1) << 2), 0);
if (!(meminfo->dimm_mask & 0x0F) && (meminfo->dimm_mask & 0xF0)) { /* channelB only? */
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 4) << 2), 0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 5) << 2), 0);
} else {
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 0) << 2), 0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 1) << 2), 0);
if (meminfo->sz[index].rank == 4) {
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 4) << 2), 0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 5) << 2), 0);
if (meminfo->sz[index].rank == 4) {
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 4) << 2), 0);
pci_write_config32(ctrl->f2, DRAM_CSBASE + (((index << 1) + 5) << 2), 0);
static long spd_handle_unbuffered_dimms(const struct mem_controller *ctrl,
struct mem_info *meminfo)
{
static long spd_handle_unbuffered_dimms(const struct mem_controller *ctrl,
struct mem_info *meminfo)
{
/* Abort if the chips don't support a common CAS latency. */
common_cl = spd_read_byte(device0, 18) & spd_read_byte(device1, 18);
if (!common_cl) {
/* Abort if the chips don't support a common CAS latency. */
common_cl = spd_read_byte(device0, 18) & spd_read_byte(device1, 18);
if (!common_cl) {
dcl = pci_read_config32(ctrl->f2, DRAM_CONFIG_LOW);
dcl &= ~DCL_BurstLength32; /* 32byte mode may be preferred in platforms that include graphics controllers that generate a lot of 32-bytes system memory accesses
32byte mode is not supported when the DRAM interface is 128 bits wides, even 32byte mode is set, system still use 64 byte mode */
dcl = pci_read_config32(ctrl->f2, DRAM_CONFIG_LOW);
dcl &= ~DCL_BurstLength32; /* 32byte mode may be preferred in platforms that include graphics controllers that generate a lot of 32-bytes system memory accesses
32byte mode is not supported when the DRAM interface is 128 bits wides, even 32byte mode is set, system still use 64 byte mode */
if (((meminfo->dimm_mask >> DIMM_SOCKETS) & ((1 << DIMM_SOCKETS) - 1))) {
/* mux capable and single dimm in channelB */
if (mux_cap) {
if (((meminfo->dimm_mask >> DIMM_SOCKETS) & ((1 << DIMM_SOCKETS) - 1))) {
/* mux capable and single dimm in channelB */
if (mux_cap) {
dcm = pci_read_config32(ctrl->f2, DRAM_CTRL_MISC);
dcm |= DCM_Mode64BitMux;
pci_write_config32(ctrl->f2, DRAM_CTRL_MISC, dcm);
dcm = pci_read_config32(ctrl->f2, DRAM_CTRL_MISC);
dcm |= DCM_Mode64BitMux;
pci_write_config32(ctrl->f2, DRAM_CTRL_MISC, dcm);
} else { /* unmatched dual dimms ? */
/* unmatched dual dimms not supported by meminit code. Use single channelA dimm. */
meminfo->dimm_mask &= ~((1 << (DIMM_SOCKETS * 2)) - (1 << DIMM_SOCKETS));
} else { /* unmatched dual dimms ? */
/* unmatched dual dimms not supported by meminit code. Use single channelA dimm. */
meminfo->dimm_mask &= ~((1 << (DIMM_SOCKETS * 2)) - (1 << DIMM_SOCKETS));
/*15*/ 200, 160, 120, 100,
};
/*15*/ 200, 160, 120, 100,
};
value = pci_read_config32(ctrl->f3, NORTHBRIDGE_CAP);
min_cycle_time = min_cycle_times[(value >> NBCAP_MEMCLK_SHIFT) & NBCAP_MEMCLK_MASK];
bios_cycle_time = min_cycle_times[
value = pci_read_config32(ctrl->f3, NORTHBRIDGE_CAP);
min_cycle_time = min_cycle_times[(value >> NBCAP_MEMCLK_SHIFT) & NBCAP_MEMCLK_MASK];
bios_cycle_time = min_cycle_times[
- read_option(CMOS_VSTART_max_mem_clock, CMOS_VLEN_max_mem_clock, 0)];
+#ifdef CMOS_VSTART_max_mem_clock
+ read_option(max_mem_clock, 0)
+#else
+#if defined(CONFIG_MAX_MEM_CLOCK)
+ CONFIG_MAX_MEM_CLOCK
+#else
+ 0 // use DDR400 as default
+#endif
+#endif
+ ];
+
}
/* Make a second pass through the dimms and disable
* any that cannot support the selected memclk and cas latency.
}
/* Make a second pass through the dimms and disable
* any that cannot support the selected memclk and cas latency.
- value = spd_read_byte(spd_device, latency_indicies[index]);
- if (value < 0) goto hw_error;
+ val = spd_read_byte(spd_device, latency_indicies[index]);
+ if (val < 0) goto hw_error;
value |= result.param->dch_memclk << DCH_MemClkFreq_SHIFT;
pci_write_config32(ctrl->f2, DRAM_CONFIG_HIGH, value);
value |= result.param->dch_memclk << DCH_MemClkFreq_SHIFT;
pci_write_config32(ctrl->f2, DRAM_CONFIG_HIGH, value);
/* Update DRAM Timing Low with our selected cas latency */
value = pci_read_config32(ctrl->f2, DRAM_TIMING_LOW);
/* Update DRAM Timing Low with our selected cas latency */
value = pci_read_config32(ctrl->f2, DRAM_TIMING_LOW);
printk_raminit("update_dimm_Trc: clocks = %i\n", clocks);
if (clocks < DTL_TRC_MIN) {
printk_raminit("update_dimm_Trc: clocks = %i\n", clocks);
if (clocks < DTL_TRC_MIN) {
-#warning We should die here or at least disable this bank.
- printk_notice("update_dimm_Trc: can't refresh fast enough, "
- "want %i clocks, can %i clocks\n", clocks, DTL_TRC_MIN);
+ // We might want to die here instead or (at least|better) disable this bank.
+ printk(BIOS_NOTICE, "update_dimm_Trc: Can't refresh fast enough, "
+ "want %i clocks, minimum is %i clocks.\n", clocks, DTL_TRC_MIN);
static int update_dimm_Trcd(const struct mem_controller *ctrl,
const struct mem_param *param, int i, long dimm_mask)
{
static int update_dimm_Trcd(const struct mem_controller *ctrl,
const struct mem_param *param, int i, long dimm_mask)
{
dtl = pci_read_config32(ctrl->f2, DRAM_TIMING_LOW);
old_clocks = ((dtl >> DTL_TRAS_SHIFT) & DTL_TRAS_MASK) + DTL_TRAS_BASE;
if (old_clocks >= clocks) { // someone did it?
return 1;
}
dtl = pci_read_config32(ctrl->f2, DRAM_TIMING_LOW);
old_clocks = ((dtl >> DTL_TRAS_SHIFT) & DTL_TRAS_MASK) + DTL_TRAS_BASE;
if (old_clocks >= clocks) { // someone did it?
return 1;
}
dtl &= ~(DTL_TRAS_MASK << DTL_TRAS_SHIFT);
dtl |= ((clocks - DTL_TRAS_BASE) << DTL_TRAS_SHIFT);
pci_write_config32(ctrl->f2, DRAM_TIMING_LOW, dtl);
dtl &= ~(DTL_TRAS_MASK << DTL_TRAS_SHIFT);
dtl |= ((clocks - DTL_TRAS_BASE) << DTL_TRAS_SHIFT);
pci_write_config32(ctrl->f2, DRAM_TIMING_LOW, dtl);
static void set_4RankRDimm(const struct mem_controller *ctrl,
const struct mem_param *param, struct mem_info *meminfo)
{
static void set_4RankRDimm(const struct mem_controller *ctrl,
const struct mem_param *param, struct mem_info *meminfo)
{
static uint32_t get_extra_dimm_mask(const struct mem_controller *ctrl,
struct mem_info *meminfo)
{
static uint32_t get_extra_dimm_mask(const struct mem_controller *ctrl,
struct mem_info *meminfo)
{
static void set_ecc(const struct mem_controller *ctrl,
const struct mem_param *param, struct mem_info *meminfo)
{
static void set_ecc(const struct mem_controller *ctrl,
const struct mem_param *param, struct mem_info *meminfo)
{
- if (read_option(CMOS_VSTART_ECC_memory, CMOS_VLEN_ECC_memory, 1) == 0) {
+#ifdef CMOS_VSTART_ECC_memory
+ if (read_option(ECC_memory, 1) == 0) {
pci_write_config32(ctrl->f2, DRAM_CONFIG_LOW, dcl);
meminfo->is_ecc = 1;
if (!(dcl & DCL_DimmEccEn)) {
meminfo->is_ecc = 0;
pci_write_config32(ctrl->f2, DRAM_CONFIG_LOW, dcl);
meminfo->is_ecc = 1;
if (!(dcl & DCL_DimmEccEn)) {
meminfo->is_ecc = 0;
if (!(meminfo->dimm_mask & (1 << i))) {
if (meminfo->dimm_mask & (1 << (DIMM_SOCKETS + i))) { /* channelB only? */
spd_device = ctrl->channel1[i];
if (!(meminfo->dimm_mask & (1 << i))) {
if (meminfo->dimm_mask & (1 << (DIMM_SOCKETS + i))) { /* channelB only? */
spd_device = ctrl->channel1[i];
set_TT(ctrl, param, DRAM_TIMING_HIGH, DTH_TWRWR_SHIFT, DTH_TWRWR_MASK,DTH_TWRWR_BASE, DTH_TWRWR_MIN, DTH_TWRWR_MAX, param->Twrwr, "Twrwr");
}
set_TT(ctrl, param, DRAM_TIMING_HIGH, DTH_TWRWR_SHIFT, DTH_TWRWR_MASK,DTH_TWRWR_BASE, DTH_TWRWR_MIN, DTH_TWRWR_MAX, param->Twrwr, "Twrwr");
}
static void set_Trdrd(const struct mem_controller *ctrl, const struct mem_param *param)
{
set_TT(ctrl, param, DRAM_TIMING_HIGH, DTH_TRDRD_SHIFT, DTH_TRDRD_MASK,DTH_TRDRD_BASE, DTH_TRDRD_MIN, DTH_TRDRD_MAX, param->Trdrd, "Trdrd");
}
static void set_Trdrd(const struct mem_controller *ctrl, const struct mem_param *param)
{
set_TT(ctrl, param, DRAM_TIMING_HIGH, DTH_TRDRD_SHIFT, DTH_TRDRD_MASK,DTH_TRDRD_BASE, DTH_TRDRD_MIN, DTH_TRDRD_MAX, param->Trdrd, "Trdrd");
}
static void set_DcqBypassMax(const struct mem_controller *ctrl, const struct mem_param *param)
{
set_TT(ctrl, param, DRAM_CONFIG_HIGH, DCH_DcqBypassMax_SHIFT, DCH_DcqBypassMax_MASK,DCH_DcqBypassMax_BASE, DCH_DcqBypassMax_MIN, DCH_DcqBypassMax_MAX, param->DcqByPassMax, "DcqBypassMax"); // value need to be in CMOS
}
static void set_DcqBypassMax(const struct mem_controller *ctrl, const struct mem_param *param)
{
set_TT(ctrl, param, DRAM_CONFIG_HIGH, DCH_DcqBypassMax_SHIFT, DCH_DcqBypassMax_MASK,DCH_DcqBypassMax_BASE, DCH_DcqBypassMax_MIN, DCH_DcqBypassMax_MAX, param->DcqByPassMax, "DcqBypassMax"); // value need to be in CMOS
}
static void set_Tfaw(const struct mem_controller *ctrl, const struct mem_param *param, struct mem_info *meminfo)
{
static const uint8_t faw_1k[] = {8, 10, 13, 14};
static void set_Tfaw(const struct mem_controller *ctrl, const struct mem_param *param, struct mem_info *meminfo)
{
static const uint8_t faw_1k[] = {8, 10, 13, 14};
}
set_TT(ctrl, param, DRAM_CONFIG_HIGH, DCH_FourActWindow_SHIFT, DCH_FourActWindow_MASK, DCH_FourActWindow_BASE, DCH_FourActWindow_MIN, DCH_FourActWindow_MAX, faw, "FourActWindow");
}
set_TT(ctrl, param, DRAM_CONFIG_HIGH, DCH_FourActWindow_SHIFT, DCH_FourActWindow_MASK, DCH_FourActWindow_BASE, DCH_FourActWindow_MIN, DCH_FourActWindow_MAX, faw, "FourActWindow");
static void set_RDqsEn(const struct mem_controller *ctrl,
const struct mem_param *param, struct mem_info *meminfo)
{
static void set_RDqsEn(const struct mem_controller *ctrl,
const struct mem_param *param, struct mem_info *meminfo)
{
static void set_idle_cycle_limit(const struct mem_controller *ctrl,
const struct mem_param *param)
{
static void set_idle_cycle_limit(const struct mem_controller *ctrl,
const struct mem_param *param)
{
static void set_RdWrQByp(const struct mem_controller *ctrl,
const struct mem_param *param)
{
set_TT(ctrl, param, DRAM_CTRL_MISC, DCM_RdWrQByp_SHIFT, DCM_RdWrQByp_MASK,0, 0, 3, 2, "RdWrQByp");
}
static void set_RdWrQByp(const struct mem_controller *ctrl,
const struct mem_param *param)
{
set_TT(ctrl, param, DRAM_CTRL_MISC, DCM_RdWrQByp_SHIFT, DCM_RdWrQByp_MASK,0, 0, 3, 2, "RdWrQByp");
}
static long spd_set_dram_timing(const struct mem_controller *ctrl,
const struct mem_param *param,
struct mem_info *meminfo)
static long spd_set_dram_timing(const struct mem_controller *ctrl,
const struct mem_param *param,
struct mem_info *meminfo)
static uint32_t hoist_memory(int controllers, const struct mem_controller *ctrl,unsigned hole_startk, int i)
{
int ii;
static uint32_t hoist_memory(int controllers, const struct mem_controller *ctrl,unsigned hole_startk, int i)
{
int ii;
/* We need to double check if the hole_startk is valid, if it is equal
to basek, we need to decrease it some */
uint32_t basek_pri;
/* We need to double check if the hole_startk is valid, if it is equal
to basek, we need to decrease it some */
uint32_t basek_pri;
static void sdram_enable(int controllers, const struct mem_controller *ctrl,
struct sys_info *sysinfo)
{
int i;
static void sdram_enable(int controllers, const struct mem_controller *ctrl,
struct sys_info *sysinfo)
{
int i;
/* Error if I don't have memory */
if (memory_end_k(ctrl, controllers) == 0) {
/* Error if I don't have memory */
if (memory_end_k(ctrl, controllers) == 0) {
if (!sysinfo->ctrl_present[ i ])
continue;
dch = pci_read_config32(ctrl[i].f2, DRAM_CONFIG_HIGH);
if (!sysinfo->ctrl_present[ i ])
continue;
dch = pci_read_config32(ctrl[i].f2, DRAM_CONFIG_HIGH);
/* We need to wait a minimum of 20 MEMCLKS to enable the InitDram */
memreset(controllers, ctrl);
/* We need to wait a minimum of 20 MEMCLKS to enable the InitDram */
memreset(controllers, ctrl);
-#if 0
- printk_debug("prepare to InitDram:");
- for (i=0; i<10; i++) {
- printk_debug("%08x", i);
- print_debug("\b\b\b\b\b\b\b\b");
+
+ /* lets override the rest of the routine */
+ if (suspend) {
+ printk(BIOS_DEBUG, "Wakeup!\n");
+ exit_from_self(controllers, ctrl, sysinfo);
+ printk(BIOS_DEBUG, "Mem running !\n");
+ return;
dcl = pci_read_config32(ctrl[i].f2, DRAM_CONFIG_LOW);
if (dcl & DCL_DimmEccEn) {
uint32_t mnc;
dcl = pci_read_config32(ctrl[i].f2, DRAM_CONFIG_LOW);
if (dcl & DCL_DimmEccEn) {
uint32_t mnc;
mnc = pci_read_config32(ctrl[i].f3, MCA_NB_CONFIG);
mnc |= MNC_ECC_EN;
if (dcl & DCL_Width128) {
mnc = pci_read_config32(ctrl[i].f3, MCA_NB_CONFIG);
mnc |= MNC_ECC_EN;
if (dcl & DCL_Width128) {
-#if 0
- /* Set the DqsRcvEnTrain bit */
- dword = pci_read_config32(ctrl[i].f2, DRAM_CTRL);
- dword |= DC_DqsRcvEnTrain;
- pci_write_config32(ctrl[i].f2, DRAM_CTRL, dword);
-#endif
-
pci_write_config32(ctrl[i].f2, DRAM_CONFIG_LOW, dcl);
dcl |= DCL_InitDram;
pci_write_config32(ctrl[i].f2, DRAM_CONFIG_LOW, dcl);
}
for (i = 0; i < controllers; i++) {
pci_write_config32(ctrl[i].f2, DRAM_CONFIG_LOW, dcl);
dcl |= DCL_InitDram;
pci_write_config32(ctrl[i].f2, DRAM_CONFIG_LOW, dcl);
}
for (i = 0; i < controllers; i++) {
if (!sysinfo->ctrl_present[ i ])
continue;
/* Skip everything if I don't have any memory on this controller */
if (sysinfo->meminfo[i].dimm_mask==0x00) continue;
if (!sysinfo->ctrl_present[ i ])
continue;
/* Skip everything if I don't have any memory on this controller */
if (sysinfo->meminfo[i].dimm_mask==0x00) continue;
int loops = 0;
do {
dcl = pci_read_config32(ctrl[i].f2, DRAM_CONFIG_LOW);
loops++;
if ((loops & 1023) == 0) {
int loops = 0;
do {
dcl = pci_read_config32(ctrl[i].f2, DRAM_CONFIG_LOW);
loops++;
if ((loops & 1023) == 0) {
print_debug_dqs_tsc(" dtsc0", i, tsc0[i].hi, tsc0[i].lo, 2);
}
#endif
print_debug_dqs_tsc(" dtsc0", i, tsc0[i].hi, tsc0[i].lo, 2);
}
#endif
/* init hw mem hole here */
/* DramHoleValid bit only can be set after MemClrStatus is set by Hardware */
set_hw_mem_hole(controllers, ctrl);
/* init hw mem hole here */
/* DramHoleValid bit only can be set after MemClrStatus is set by Hardware */
set_hw_mem_hole(controllers, ctrl);
#if K8_REV_F_SUPPORT_F0_F1_WORKAROUND == 1
dqs_timing(controllers, ctrl, tsc0, sysinfo);
#else
#if K8_REV_F_SUPPORT_F0_F1_WORKAROUND == 1
dqs_timing(controllers, ctrl, tsc0, sysinfo);
#else
/* need to enable mtrr, so dqs training could access the test address */
setup_mtrr_dqs(sysinfo->tom_k, sysinfo->tom2_k);
#endif
/* need to enable mtrr, so dqs training could access the test address */
setup_mtrr_dqs(sysinfo->tom_k, sysinfo->tom2_k);
#endif
dqs_timing(i, &ctrl[i], sysinfo, 1);
dqs_timing(i, &ctrl[i], sysinfo, 1);
-
-static void fill_mem_ctrl(int controllers, struct mem_controller *ctrl_a,
- const uint16_t *spd_addr)
+void fill_mem_ctrl(int controllers, struct mem_controller *ctrl_a,
+ const uint16_t *spd_addr)