Following patch will setup KT890 HT automatically. It will find the

max width of the link and also it will take the frequency of K8 HT
already done coreboot (and checks if t can run on it).

Signed-off-by: Rudolf Marek <r.marek@assembler.cz>

Acked-by: Uwe Hermann <uwe@hermann-uwe.de>



git-svn-id: svn://svn.coreboot.org/coreboot/trunk@3169 2b7e53f0-3cfb-0310-b3e9-8179ed1497e1
This commit is contained in:
Rudolf Marek 2008-03-19 20:24:33 +00:00
parent cfcc9ca590
commit c221349746
3 changed files with 63 additions and 25 deletions

View File

@ -5,6 +5,9 @@
#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0])) #define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[0]))
#define MIN(a,b) ((a) < (b) ? (a) : (b))
#define MAX(a,b) ((a) > (b) ? (a) : (b))
#ifndef __ROMCC__ #ifndef __ROMCC__
extern void *malloc(size_t size); extern void *malloc(size_t size);
void free(void *ptr); void free(void *ptr);

View File

@ -284,20 +284,19 @@ void real_main(unsigned long bist, unsigned long cpu_init_detectedx)
init_timer(); init_timer();
ht_setup_chains_x(sysinfo); /* Init sblnk and sbbusn, nodes, sbdn. */ ht_setup_chains_x(sysinfo); /* Init sblnk and sbbusn, nodes, sbdn. */
enable_fid_change();
init_fidvid_bsp(bsp_apicid);
needs_reset = optimize_link_coherent_ht(); needs_reset = optimize_link_coherent_ht();
needs_reset |= optimize_link_incoherent_ht(sysinfo); needs_reset |= optimize_link_incoherent_ht(sysinfo);
needs_reset |= k8t890_early_setup_ht();
/* FIXME: Assumes that 1000MHz LDT is selected. */
needs_reset |= k8t890_early_setup_car(16, 0x6);
if (needs_reset) { if (needs_reset) {
print_debug("ht reset -\r\n"); print_debug("ht reset -\r\n");
soft_reset(); soft_reset();
} }
/* the HT settings needs to be OK, because link freq chnage may cause HT disconnect */
enable_fid_change();
init_fidvid_bsp(bsp_apicid);
/* Stop the APs so we can start them later in init. */ /* Stop the APs so we can start them later in init. */
allow_all_aps_stop(bsp_apicid); allow_all_aps_stop(bsp_apicid);

View File

@ -22,35 +22,71 @@
* generate PCI reset or LDTSTOP to apply. * generate PCI reset or LDTSTOP to apply.
*/ */
u8 k8t890_early_setup_car(u8 width, u8 speed) #include <stdlib.h>
/* AMD K8 LDT0, LDT1, LDT2 Link Control Registers */
static ldtreg[3] = {0x86, 0xa6, 0xc6};
/* This functions sets KT890 link frequency and width to same values as
* it has been setup on K8 side, by AMD NB init.
*/
u8 k8t890_early_setup_ht(void)
{ {
u8 awidth, aspeed; u8 awidth, afreq, cldtfreq;
u8 cldtwidth_in, cldtwidth_out, vldtwidth_in, vldtwidth_out, ldtnr, width;
u16 vldtcaps;
print_debug("LDT width and speed for K8T890 was"); /* check if connected non coherent, initcomplete (find the SB on K8 side) */
awidth = pci_read_config8(PCI_DEV(0, 0x0, 0), 0x67); if (0x7 == pci_read_config8(PCI_DEV(0, 0x18, 0), 0x98)) {
print_debug_hex8(awidth); ldtnr = 0;
} else if (0x7 == pci_read_config8(PCI_DEV(0, 0x18, 0), 0xb8)) {
ldtnr = 1;
} else if (0x7 == pci_read_config8(PCI_DEV(0, 0x18, 0), 0xd8)) {
ldtnr = 2;
}
aspeed = pci_read_config8(PCI_DEV(0, 0x0, 0), 0x6d); print_debug("K8T890 found at LDT ");
print_debug_hex8(aspeed); print_debug_hex8(ldtnr);
if ((aspeed == speed) && (((width == 16) && (awidth == 0x11)) || /* get the maximum widths for both sides */
((width == 8) && (awidth == 0x00)))) cldtwidth_in = pci_read_config8(PCI_DEV(0, 0x18, 0), ldtreg[ldtnr]) & 0x7;
return 0; cldtwidth_out = (pci_read_config8(PCI_DEV(0, 0x18, 0), ldtreg[ldtnr]) >> 4) & 0x7;
vldtwidth_in = pci_read_config8(PCI_DEV(0, 0x0, 0), 0x66) & 0x7;
vldtwidth_out = (pci_read_config8(PCI_DEV(0, 0x0, 0), 0x66) >> 4) & 0x7;
/* Update the desired HT LNK capabilities in NB too. */ width = MIN(MIN(MIN(cldtwidth_out, cldtwidth_in), vldtwidth_out), vldtwidth_in);
pci_write_config8(PCI_DEV(0, 0x0, 0), 0x67, print_debug(" Agreed on width: ");
(width == 16) ? 0x11 : 0x00); print_debug_hex8(width);
pci_write_config8(PCI_DEV(0, 0x0, 0), 0x6d, speed);
print_debug(" and will after HT reset: ");
awidth = pci_read_config8(PCI_DEV(0, 0x0, 0), 0x67); awidth = pci_read_config8(PCI_DEV(0, 0x0, 0), 0x67);
print_debug_hex8(awidth);
aspeed = pci_read_config8(PCI_DEV(0, 0x0, 0), 0x6d); /* Update the desired HT LNK to match AMD NB max from VIA NB is 0x1 */
print_debug_hex8(aspeed); width = (width == 0x01) ? 0x11 : 0x00;
pci_write_config8(PCI_DEV(0, 0x0, 0), 0x67, width);
/* Get programmed HT freq at base 0x89 */
cldtfreq = pci_read_config8(PCI_DEV(0, 0x18, 0), ldtreg[ldtnr] + 3) & 0xf;
print_debug(" CPU programmed to HT freq: ");
print_debug_hex8(cldtfreq);
print_debug(" VIA HT caps: ");
vldtcaps = pci_read_config16(PCI_DEV(0, 0, 0), 0x6e);
print_debug_hex16(vldtcaps);
if (!(vldtcaps & (1 << cldtfreq ))) {
die("Chipset does not support desired HT frequency\n");
}
afreq = pci_read_config8(PCI_DEV(0, 0x0, 0), 0x6d);
pci_write_config8(PCI_DEV(0, 0x0, 0), 0x6d, cldtfreq);
print_debug("\n"); print_debug("\n");
/* no reset needed */
if ((width == awidth) && (afreq == cldtfreq)) {
return 0;
}
return 1; return 1;
} }