aboutsummaryrefslogtreecommitdiff
path: root/src/northbridge/amd/lx/northbridge.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/northbridge/amd/lx/northbridge.c')
-rw-r--r--src/northbridge/amd/lx/northbridge.c317
1 files changed, 27 insertions, 290 deletions
diff --git a/src/northbridge/amd/lx/northbridge.c b/src/northbridge/amd/lx/northbridge.c
index b014118da8..88dfe12523 100644
--- a/src/northbridge/amd/lx/northbridge.c
+++ b/src/northbridge/amd/lx/northbridge.c
@@ -1,3 +1,9 @@
+/*
+*
+* Copyright (C) 2007 Advanced Micro Devices
+*
+*/
+
#include <console/console.h>
#include <arch/io.h>
#include <stdint.h>
@@ -7,13 +13,13 @@
#include <stdlib.h>
#include <string.h>
#include <bitops.h>
-#include "chip.h"
-#include "northbridge.h"
#include <cpu/cpu.h>
#include <cpu/amd/lxdef.h>
#include <cpu/x86/msr.h>
#include <cpu/x86/cache.h>
#include <cpu/amd/vr.h>
+#include "chip.h"
+#include "northbridge.h"
/* here is programming for the various MSRs.*/
@@ -56,9 +62,11 @@
extern void graphics_init(void);
extern void cpubug(void);
+extern void chipsetinit(void);
+extern void print_conf(void);
+extern uint32_t get_systop(void);
void northbridge_init_early(void);
-void chipsetinit(struct northbridge_amd_lx_config *nb);
void setup_realmode_idt(void);
void do_vsmbios(void);
@@ -97,309 +105,42 @@ struct msr_defaults {
/* todo: add a resource record. We don't do this here because this may be called when
* very little of the platform is actually working.
*/
-int
-sizeram(void)
+int sizeram(void)
{
msr_t msr;
int sizem = 0;
unsigned short dimm;
- msr = rdmsr(0x20000018);
- printk_debug("sizeram: %08x:%08x\n", msr.hi, msr.lo);
+ msr = rdmsr(MC_CF07_DATA);
+ printk_debug("sizeram: _MSR MC_CF07_DATA: %08x:%08x\n", msr.hi, msr.lo);
/* dimm 0 */
dimm = msr.hi;
- sizem = (1 << ((dimm >> 12)-1)) * 8;
-
+ /* installed? */
+ if ((dimm & 7) != 7){
+ sizem = 4 << ((dimm >> 12) & 0x0F);
+ }
/* dimm 1*/
dimm = msr.hi >> 16;
/* installed? */
- if ((dimm & 7) != 7)
- sizem += (1 << ((dimm >> 12)-1)) * 8;
+ if ((dimm & 7) != 7){
+ sizem += 4 << ((dimm >> 12) & 0x0F);
+ }
- printk_debug("sizeram: sizem 0x%x\n", sizem);
+ printk_debug("sizeram: sizem 0x%xMB\n", sizem);
return sizem;
}
-/* note that dev is NOT used -- yet */
-static void irq_init_steering(struct device *dev, uint16_t irq_map) {
- /* Set up IRQ steering */
- uint32_t pciAddr = 0x80000000 | (CHIPSET_DEV_NUM << 11) | 0x5C;
-
- printk_debug("%s(%08X [%08X], %04X)\n", __FUNCTION__, dev, pciAddr, irq_map);
-
- /* The IRQ steering values (in hex) are effectively dcba, where:
- * <a> represents the IRQ for INTA,
- * <b> represents the IRQ for INTB,
- * <c> represents the IRQ for INTC, and
- * <d> represents the IRQ for INTD.
- * Thus, a value of irq_map = 0xAA5B translates to:
- * INTA = IRQB (IRQ 11)
- * INTB = IRQ5 (IRQ 5)
- * INTC = IRQA (IRQ 10)
- * INTD = IRQA (IRQ 10)
- */
- outl(pciAddr & ~3, 0xCF8);
- outl(irq_map, 0xCFC);
-}
-/*
- * setup_lx_cache
- *
- * Returns the amount of memory (in KB) available to the system. This is the
- * total amount of memory less the amount of memory reserved for SMM use.
- *
- */
-static int
-setup_lx_cache(void)
-{
- msr_t msr;
- unsigned long long val;
- int sizekbytes, sizereg;
-
- sizekbytes = sizeram() * 1024;
- printk_debug("setup_lx_cache: enable for %d KB\n", sizekbytes);
- /* build up the rconf word. */
- /* the SYSTOP bits 27:8 are actually the top bits from 31:12. Book fails to say that */
- /* set romrp */
- val = ((unsigned long long) ROM_PROPERTIES) << 56;
- /* make rom base useful for 1M roms */
- /* Flash base address -- sized for 1M for now*/
- val |= ((unsigned long long) 0xfff00)<<36;
- /* set the devrp properties */
- val |= ((unsigned long long) DEVICE_PROPERTIES) << 28;
- /* Take our TOM, RIGHT shift 12, since it page-aligned, then LEFT-shift 8 for reg. */
- /* yank off memory for the SMM handler */
- sizekbytes -= SMM_SIZE;
- sizereg = sizekbytes;
- sizereg >>= 2;
- sizereg <<= 8;
- val |= sizereg;
- val |= RAM_PROPERTIES;
- msr.lo = val;
- msr.hi = (val >> 32);
-
- // GX3
- //msr.hi = 0x04FFFC02;
- //msr.lo = 0x1077BE00;
-
- //sizekbytes = 122616;
-
- printk_debug("msr 0x%08X will be set to %08x:%08x\n", CPU_RCONF_DEFAULT, msr.hi, msr.lo);
- wrmsr(CPU_RCONF_DEFAULT, msr);
-
- enable_cache();
- wbinvd();
- return sizekbytes;
-}
-
-/* we have to do this here. We have not found a nicer way to do it */
-void
-setup_lx(void)
-{
-
- unsigned long tmp, tmp2;
- msr_t msr;
- unsigned long size_kb, membytes;
-
- size_kb = setup_lx_cache();
-
-#if 0 // andrei: this is done in northbridge.c SMMGL0Init and SystemInit!
- membytes = size_kb * 1024;
- /* NOTE! setup_lx_cache returns the SIZE OF RAM - RAMADJUST!
- * so it is safe to use. You should NOT at this point call
- * sizeram() directly.
- */
-
- /* we need to set 0x10000028 and 0x40000029 */
- /*
- * These two descriptors cover the range from 1 MB (0x100000) to
- * SYSTOP (a.k.a. TOM, or Top of Memory)
- */
-
-
- /* fixme: SMM MSR 0x10000026 and 0x400000023 */
- /* calculate the OFFSET field */
- tmp = membytes - SMM_OFFSET;
- tmp >>= 12;
- tmp <<= 8;
- tmp |= 0x20000000;
- tmp |= (SMM_OFFSET >> 24);
-
- /* calculate the PBASE and PMASK fields */
- tmp2 = (SMM_OFFSET << 8) & 0xFFF00000; /* shift right 12 then left 20 == left 8 */
- tmp2 |= (((~(SMM_SIZE * 1024) + 1) >> 12) & 0xfffff);
- printk_debug("MSR 0x%x is now 0x%x:0x%x\n", 0x10000026, tmp, tmp2);
- msr.hi = tmp;
- msr.lo = tmp2;
- wrmsr(0x10000026, msr);
-#endif
-}
-
static void enable_shadow(device_t dev)
{
}
-void print_conf(void) {
- int i;
- unsigned long iol;
- msr_t msr;
-
- int cpu_msr_defs[] = { L2_CONFIG_MSR, CPU_IM_CONFIG,
- CPU_DM_CONFIG0, CPU_DM_CONFIG1, CPU_DM_PFLOCK, CPU_RCONF_DEFAULT,
- CPU_RCONF_BYPASS, CPU_RCONF_A0_BF, CPU_RCONF_C0_DF, CPU_RCONF_E0_FF,
- CPU_RCONF_SMM, CPU_RCONF_DMM, GLCP_DELAY_CONTROLS, GL_END
- };
-
- int gliu0_msr_defs[] = {MSR_GLIU0_BASE1, MSR_GLIU0_BASE2, MSR_GLIU0_BASE3, MSR_GLIU0_BASE4, MSR_GLIU0_BASE5, MSR_GLIU0_BASE6,
- GLIU0_P2D_BMO_0, GLIU0_P2D_BMO_1, MSR_GLIU0_SYSMEM,
- GLIU0_P2D_RO_0, GLIU0_P2D_RO_1, GLIU0_P2D_RO_2, MSR_GLIU0_SHADOW,
- GLIU0_IOD_BM_0, GLIU0_IOD_BM_1, GLIU0_IOD_BM_2,
- GLIU0_IOD_SC_0, GLIU0_IOD_SC_1, GLIU0_IOD_SC_2, GLIU0_IOD_SC_3, GLIU0_IOD_SC_4, GLIU0_IOD_SC_5,
- GLIU0_GLD_MSR_COH, GL_END
- };
-
- int gliu1_msr_defs[] = {MSR_GLIU1_BASE1, MSR_GLIU1_BASE2, MSR_GLIU1_BASE3, MSR_GLIU1_BASE4, MSR_GLIU1_BASE5, MSR_GLIU1_BASE6,
- MSR_GLIU1_BASE7, MSR_GLIU1_BASE8, MSR_GLIU1_BASE9, MSR_GLIU1_BASE10,
- GLIU1_P2D_R_0, GLIU1_P2D_R_1, GLIU1_P2D_R_2, GLIU1_P2D_R_3, MSR_GLIU1_SHADOW,
- GLIU1_IOD_BM_0, GLIU1_IOD_BM_1, GLIU1_IOD_BM_2,
- GLIU1_IOD_SC_0, GLIU1_IOD_SC_1, GLIU1_IOD_SC_2, GLIU1_IOD_SC_3,
- GLIU1_GLD_MSR_COH, GL_END
- };
-
- int rconf_msr[] = { CPU_RCONF0, CPU_RCONF1, CPU_RCONF2, CPU_RCONF3, CPU_RCONF4,
- CPU_RCONF5, CPU_RCONF6, CPU_RCONF7, GL_END
- };
-
- int cs5536_msr[] = { MDD_LBAR_GPIO, MDD_LBAR_FLSH0, MDD_LBAR_FLSH1, MDD_LEG_IO, MDD_PIN_OPT,
- MDD_IRQM_ZLOW, MDD_IRQM_ZHIGH, MDD_IRQM_PRIM, GL_END
- };
-
- int pci_msr[] = { GLPCI_CTRL, GLPCI_ARB, GLPCI_REN, GLPCI_A0_BF, GLPCI_C0_DF, GLPCI_E0_FF,
- GLPCI_RC0, GLPCI_RC1, GLPCI_RC2, GLPCI_RC3, GLPCI_EXT_MSR, GLPCI_SPARE,
- GL_END
- };
-
- int dma_msr[] = { MDD_DMA_MAP, MDD_DMA_SHAD1, MDD_DMA_SHAD2, MDD_DMA_SHAD3, MDD_DMA_SHAD4,
- MDD_DMA_SHAD5, MDD_DMA_SHAD6, MDD_DMA_SHAD7, MDD_DMA_SHAD8,
- MDD_DMA_SHAD9, GL_END
- };
-
-
- printk_debug("---------- CPU ------------\n");
-
- for(i = 0; cpu_msr_defs[i] != GL_END; i++) {
- msr = rdmsr(cpu_msr_defs[i]);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", cpu_msr_defs[i], msr.hi, msr.lo);
- }
-
- printk_debug("---------- GLIU 0 ------------\n");
-
- for(i = 0; gliu0_msr_defs[i] != GL_END; i++) {
- msr = rdmsr(gliu0_msr_defs[i]);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", gliu0_msr_defs[i], msr.hi, msr.lo);
- }
-
- printk_debug("---------- GLIU 1 ------------\n");
-
- for(i = 0; gliu1_msr_defs[i] != GL_END; i++) {
- msr = rdmsr(gliu1_msr_defs[i]);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", gliu1_msr_defs[i], msr.hi, msr.lo);
- }
-
- printk_debug("---------- RCONF ------------\n");
-
- for(i = 0; rconf_msr[i] != GL_END; i++) {
- msr = rdmsr(rconf_msr[i]);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", rconf_msr[i], msr.hi, msr.lo);
- }
-
- printk_debug("---------- VARIA ------------\n");
- msr = rdmsr(0x51300010);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", 0x51300010, msr.hi, msr.lo);
-
- msr = rdmsr(0x51400015);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", 0x51400015, msr.hi, msr.lo);
-
- printk_debug("---------- DIVIL IRQ ------------\n");
- msr = rdmsr(MDD_IRQM_YLOW);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", MDD_IRQM_YLOW, msr.hi, msr.lo);
- msr = rdmsr(MDD_IRQM_YHIGH);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", MDD_IRQM_YHIGH, msr.hi, msr.lo);
- msr = rdmsr(MDD_IRQM_ZLOW);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", MDD_IRQM_ZLOW, msr.hi, msr.lo);
- msr = rdmsr(MDD_IRQM_ZHIGH);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", MDD_IRQM_ZHIGH, msr.hi, msr.lo);
-
-
- printk_debug("---------- PCI ------------\n");
-
- for(i = 0; pci_msr[i] != GL_END; i++) {
- msr = rdmsr(pci_msr[i]);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", pci_msr[i], msr.hi, msr.lo);
- }
-
- printk_debug("---------- LPC/UART DMA ------------\n");
-
- for(i = 0; dma_msr[i] != GL_END; i++) {
- msr = rdmsr(dma_msr[i]);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", dma_msr[i], msr.hi, msr.lo);
- }
-
- printk_debug("---------- CS5536 ------------\n");
-
- for(i = 0; cs5536_msr[i] != GL_END; i++) {
- msr = rdmsr(cs5536_msr[i]);
- printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", cs5536_msr[i], msr.hi, msr.lo);
- }
-
- iol = inl(GPIOL_INPUT_ENABLE);
- printk_debug("IOR 0x%08X is now 0x%08X\n", GPIOL_INPUT_ENABLE, iol);
- iol = inl(GPIOL_EVENTS_ENABLE);
- printk_debug("IOR 0x%08X is now 0x%08X\n", GPIOL_EVENTS_ENABLE, iol);
- iol = inl(GPIOL_INPUT_INVERT_ENABLE);
- printk_debug("IOR 0x%08X is now 0x%08X\n", GPIOL_INPUT_INVERT_ENABLE, iol);
- iol = inl(GPIO_MAPPER_X);
- printk_debug("IOR 0x%08X is now 0x%08X\n", GPIO_MAPPER_X, iol);
-
-}
-
-static void enable_L2_cache(void) {
- msr_t msr;
-
- /* Instruction Memory Configuration register
- * set EBE bit, required when L2 cache is enabled
- */
- msr = rdmsr(CPU_IM_CONFIG);
- msr.lo |= 0x400;
- wrmsr(CPU_IM_CONFIG, msr);
-
- /* Data Memory Subsystem Configuration register
- * set EVCTONRPL bit, required when L2 cache is enabled in victim mode
- */
- msr = rdmsr(CPU_DM_CONFIG0);
- msr.lo |= 0x4000;
- wrmsr(CPU_DM_CONFIG0, msr);
-
- /* invalidate L2 cache */
- msr.hi = 0x00;
- msr.lo = 0x10;
- wrmsr(L2_CONFIG_MSR, msr);
-
- /* Enable L2 cache */
- msr.hi = 0x00;
- msr.lo = 0x0f;
- wrmsr(L2_CONFIG_MSR, msr);
-
- printk_debug("L2 cache enabled\n");
-}
-
static void northbridge_init(device_t dev)
{
//msr_t msr;
- struct northbridge_amd_lx_config *nb = (struct northbridge_amd_lx_config *)dev->chip_info;
printk_spew(">> Entering northbridge.c: %s\n", __FUNCTION__);
@@ -412,8 +153,6 @@ static void northbridge_init(device_t dev)
//msr.hi |= 0x3;
//msr.lo |= 0x30000;
-// not needed (also irq steering is in legacy vsm so it wouldnt work either)
-// irq_init_steering(dev, nb->irqmap);
//printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", MSR_GLIU0_SHADOW, msr.hi, msr.lo);
//printk_debug("MSR 0x%08X is now 0x%08X:0x%08X\n", MSR_GLIU1_SHADOW, msr.hi, msr.lo);
@@ -521,7 +260,7 @@ static void pci_domain_set_resources(device_t dev)
/* Report the memory regions */
idx = 10;
ram_resource(dev, idx++, 0, 640);
- ram_resource(dev, idx++, 1024, ((sizeram() - CONFIG_VIDEO_MB) * 1024) - SMM_SIZE - 1024);
+ ram_resource(dev, idx++, 1024, (get_systop()- 0x100000)/1024 ); // Systop - 1 MB -> KB
}
assign_resources(&dev->link[0]);
@@ -529,25 +268,23 @@ static void pci_domain_set_resources(device_t dev)
static void pci_domain_enable(device_t dev)
{
- struct northbridge_amd_lx_config *nb = (struct northbridge_amd_lx_config *)dev->chip_info;
printk_spew(">> Entering northbridge.c: %s\n", __FUNCTION__);
// do this here for now -- this chip really breaks our device model
- enable_L2_cache();
northbridge_init_early();
cpubug();
- chipsetinit(nb);
- setup_lx();
+ chipsetinit();
+
setup_realmode_idt();
printk_debug("Before VSA:\n");
- print_conf();
+ // print_conf();
do_vsmbios(); // do the magic stuff here, so prepare your tambourine ;)
printk_debug("After VSA:\n");
- print_conf();
+ // print_conf();
graphics_init();
pci_set_method(dev);