1 /* coherent hypertransport initialization for AMD64
3 * written by Stefan Reinauer <stepan@openbios.org>
4 * (c) 2003-2004 by SuSE Linux AG
6 * (c) 2004 Tyan Computer
7 * 2004.12 yhlu added support to create routing table dynamically.
8 * it also support 8 ways too. (8 ways ladder or 8 ways crossbar)
10 * This code is licensed under GPL.
14 * This algorithm assumes a grid configuration as follows:
17 * org. : 1x1 2x1 2x2 2x3 2x4
66 #include <device/pci_def.h>
67 #include <device/pci_ids.h>
68 #include <device/hypertransport_def.h>
70 #include "arch/romcc_io.h"
71 #include <pc80/mc146818rtc.h>
72 #if CONFIG_HAVE_OPTION_TABLE
73 #include "option_table.h"
78 #define enable_bsp_routing() enable_routing(0)
80 #define NODE_HT(x) PCI_DEV(0,24+x,0)
81 #define NODE_MP(x) PCI_DEV(0,24+x,1)
82 #define NODE_MC(x) PCI_DEV(0,24+x,3)
84 #define DEFAULT 0x00010101 /* default row entry */
87 #ifndef CROSS_BAR_47_56
88 #define CROSS_BAR_47_56 0
91 #ifndef TRY_HIGH_FIRST
92 #define TRY_HIGH_FIRST 0
95 #ifndef CONFIG_K8_HT_FREQ_1G_SUPPORT
96 #define CONFIG_K8_HT_FREQ_1G_SUPPORT 0
99 #ifndef K8_HT_CHECK_PENDING_LINK
100 #if CONFIG_MAX_PHYSICAL_CPUS >= 4
101 #define K8_HT_CHECK_PENDING_LINK 1
103 #define K8_HT_CHECK_PENDING_LINK 0
107 #ifndef CONFIG_MAX_PHYSICAL_CPUS_4_BUT_MORE_INSTALLED
108 #define CONFIG_MAX_PHYSICAL_CPUS_4_BUT_MORE_INSTALLED 0
111 #ifndef CONFIG_ENABLE_APIC_EXT_ID
112 #define CONFIG_ENABLE_APIC_EXT_ID 0
116 static inline void print_linkn (const char *strval, uint8_t byteval)
118 printk(BIOS_DEBUG, "%s%02x\n", strval, byteval);
121 static void disable_probes(void)
123 /* disable read/write/fill probes for uniprocessor setup
124 * they don't make sense if only one cpu is available
127 /* Hypetransport Transaction Control Register
129 * [ 0: 0] Disable read byte probe
131 * 1 = Probes not issued
132 * [ 1: 1] Disable Read Doubleword probe
134 * 1 = Probes not issued
135 * [ 2: 2] Disable write byte probes
137 * 1 = Probes not issued
138 * [ 3: 3] Disable Write Doubleword Probes
140 * 1 = Probes not issued.
141 * [10:10] Disable Fill Probe
142 * 0 = Probes issued for cache fills
143 * 1 = Probes not issued for cache fills.
148 print_spew("Disabling read/write/fill probes for UP... ");
150 val=pci_read_config32(NODE_HT(0), HT_TRANSACTION_CONTROL);
151 val |= HTTC_DIS_FILL_P | HTTC_DIS_RMT_MEM_C | HTTC_DIS_P_MEM_C |
152 HTTC_DIS_MTS | HTTC_DIS_WR_DW_P | HTTC_DIS_WR_B_P |
153 HTTC_DIS_RD_DW_P | HTTC_DIS_RD_B_P;
154 pci_write_config32(NODE_HT(0), HT_TRANSACTION_CONTROL, val);
156 print_spew("done.\n");
161 static void enable_apic_ext_id(u8 node)
163 #if CONFIG_ENABLE_APIC_EXT_ID==1
164 #warning "FIXME Is the right place to enable apic ext id here?"
168 val = pci_read_config32(NODE_HT(node), 0x68);
169 val |= (HTTC_APIC_EXT_SPUR | HTTC_APIC_EXT_ID | HTTC_APIC_EXT_BRD_CST);
170 pci_write_config32(NODE_HT(node), 0x68, val);
175 static void enable_routing(u8 node)
179 /* HT Initialization Control Register
181 * [ 0: 0] Routing Table Disable
182 * 0 = Packets are routed according to routing tables
183 * 1 = Packets are routed according to the default link field
184 * [ 1: 1] Request Disable (BSP should clear this)
185 * 0 = Request packets may be generated
186 * 1 = Request packets may not be generated.
187 * [ 3: 2] Default Link (Read-only)
191 * 11 = CPU on same node
193 * - Scratch bit cleared by a cold reset
194 * [ 5: 5] BIOS Reset Detect
195 * - Scratch bit cleared by a cold reset
196 * [ 6: 6] INIT Detect
197 * - Scratch bit cleared by a warm or cold reset not by an INIT
201 /* Enable routing table */
202 print_spew("Enabling routing table for node ");
203 print_spew_hex8(node);
205 val=pci_read_config32(NODE_HT(node), 0x6c);
206 val &= ~((1<<1)|(1<<0));
207 pci_write_config32(NODE_HT(node), 0x6c, val);
209 print_spew(" done.\n");
212 #if CONFIG_MAX_PHYSICAL_CPUS > 1
213 static void fill_row(u8 node, u8 row, u32 value)
215 pci_write_config32(NODE_HT(node), 0x40+(row<<2), value);
218 static u8 link_to_register(int ldt)
221 * [ 0: 3] Request Route
222 * [0] Route to this node
223 * [1] Route to Link 0
224 * [2] Route to Link 1
225 * [3] Route to Link 2
228 if (ldt&0x08) return 0x40;
229 if (ldt&0x04) return 0x20;
230 if (ldt&0x02) return 0x00;
232 /* we should never get here */
233 print_spew("Unknown Link\n");
237 static u32 get_row(u8 node, u8 row)
239 return pci_read_config32(NODE_HT(node), 0x40+(row<<2));
242 static int link_connection(u8 src, u8 dest)
244 return get_row(src, dest) & 0x0f;
247 static void rename_temp_node(u8 node)
251 print_spew("Renaming current temporary node to ");
252 print_spew_hex8(node);
254 val=pci_read_config32(NODE_HT(7), 0x60);
255 val &= (~7); /* clear low bits. */
256 val |= node; /* new node */
257 pci_write_config32(NODE_HT(7), 0x60, val);
259 print_spew(" done.\n");
262 static int verify_connection(u8 dest)
264 /* See if we have a valid connection to dest */
267 /* Verify that the coherent hypertransport link is
268 * established and actually working by reading the
269 * remode node's vendor/device id
271 val = pci_read_config32(NODE_HT(dest),0);
272 if(val != 0x11001022)
278 static uint16_t read_freq_cap(device_t dev, uint8_t pos)
280 /* Handle bugs in valid hypertransport frequency reporting */
284 freq_cap = pci_read_config16(dev, pos);
285 freq_cap &= ~(1 << HT_FREQ_VENDOR); /* Ignore Vendor HT frequencies */
287 #if CONFIG_K8_HT_FREQ_1G_SUPPORT == 1
288 #if CONFIG_K8_REV_F_SUPPORT == 0
289 if (!is_cpu_pre_e0())
296 id = pci_read_config32(dev, 0);
298 /* AMD K8 Unsupported 1Ghz? */
299 if (id == (PCI_VENDOR_ID_AMD | (0x1100 << 16))) {
300 freq_cap &= ~(1 << HT_FREQ_1000Mhz);
306 static int optimize_connection(device_t node1, uint8_t link1, device_t node2, uint8_t link2)
308 static const uint8_t link_width_to_pow2[]= { 3, 4, 0, 5, 1, 2, 0, 0 };
309 static const uint8_t pow2_to_link_width[] = { 0x7, 4, 5, 0, 1, 3 };
310 uint16_t freq_cap1, freq_cap2;
311 uint8_t width_cap1, width_cap2, width, old_width, ln_width1, ln_width2;
312 uint8_t freq, old_freq;
314 /* Set link width and frequency */
316 /* Initially assume everything is already optimized and I don't need a reset */
319 /* Get the frequency capabilities */
320 freq_cap1 = read_freq_cap(node1, link1 + PCI_HT_CAP_HOST_FREQ_CAP);
321 freq_cap2 = read_freq_cap(node2, link2 + PCI_HT_CAP_HOST_FREQ_CAP);
323 /* Calculate the highest possible frequency */
324 freq = log2(freq_cap1 & freq_cap2);
326 /* See if I am changing the link freqency */
327 old_freq = pci_read_config8(node1, link1 + PCI_HT_CAP_HOST_FREQ);
329 needs_reset |= old_freq != freq;
330 old_freq = pci_read_config8(node2, link2 + PCI_HT_CAP_HOST_FREQ);
332 needs_reset |= old_freq != freq;
334 /* Set the Calulcated link frequency */
335 pci_write_config8(node1, link1 + PCI_HT_CAP_HOST_FREQ, freq);
336 pci_write_config8(node2, link2 + PCI_HT_CAP_HOST_FREQ, freq);
338 /* Get the width capabilities */
339 width_cap1 = pci_read_config8(node1, link1 + PCI_HT_CAP_HOST_WIDTH);
340 width_cap2 = pci_read_config8(node2, link2 + PCI_HT_CAP_HOST_WIDTH);
342 /* Calculate node1's input width */
343 ln_width1 = link_width_to_pow2[width_cap1 & 7];
344 ln_width2 = link_width_to_pow2[(width_cap2 >> 4) & 7];
345 if (ln_width1 > ln_width2) {
346 ln_width1 = ln_width2;
348 width = pow2_to_link_width[ln_width1];
349 /* Calculate node1's output width */
350 ln_width1 = link_width_to_pow2[(width_cap1 >> 4) & 7];
351 ln_width2 = link_width_to_pow2[width_cap2 & 7];
352 if (ln_width1 > ln_width2) {
353 ln_width1 = ln_width2;
355 width |= pow2_to_link_width[ln_width1] << 4;
357 /* See if I am changing node1's width */
358 old_width = pci_read_config8(node1, link1 + PCI_HT_CAP_HOST_WIDTH + 1);
360 needs_reset |= old_width != width;
362 /* Set node1's widths */
363 pci_write_config8(node1, link1 + PCI_HT_CAP_HOST_WIDTH + 1, width);
365 // * Calculate node2's width */
366 width = ((width & 0x70) >> 4) | ((width & 0x7) << 4);
368 /* See if I am changing node2's width */
369 old_width = pci_read_config8(node2, link2 + PCI_HT_CAP_HOST_WIDTH + 1);
371 needs_reset |= old_width != width;
373 /* Set node2's widths */
374 pci_write_config8(node2, link2 + PCI_HT_CAP_HOST_WIDTH + 1, width);
379 static uint8_t get_linkn_first(uint8_t byte)
381 if(byte & 0x02) { byte = 0; }
382 else if(byte & 0x04) { byte = 1; }
383 else if(byte & 0x08) { byte = 2; }
387 #if TRY_HIGH_FIRST == 1
388 static uint8_t get_linkn_last(uint8_t byte)
390 if(byte & 0x02) { byte &= 0x0f; byte |= 0x00; }
391 if(byte & 0x04) { byte &= 0x0f; byte |= 0x10; }
392 if(byte & 0x08) { byte &= 0x0f; byte |= 0x20; }
397 #if (CONFIG_MAX_PHYSICAL_CPUS > 2) || (CONFIG_MAX_PHYSICAL_CPUS_4_BUT_MORE_INSTALLED == 1)
398 static uint8_t get_linkn_last_count(uint8_t byte)
401 if(byte & 0x02) { byte &= 0xcf; byte |= 0x00; byte+=0x40; }
402 if(byte & 0x04) { byte &= 0xcf; byte |= 0x10; byte+=0x40; }
403 if(byte & 0x08) { byte &= 0xcf; byte |= 0x20; byte+=0x40; }
408 static void setup_row_local(u8 source, u8 row) /* source will be 7 when it is for temp use*/
413 for(linkn = 0; linkn<3; linkn++) {
416 regpos = 0x98 + 0x20 * linkn;
417 reg = pci_read_config32(NODE_HT(source), regpos);
418 if ((reg & 0x17) != 3) continue; /* it is not conherent or not connected*/
423 fill_row(source,row, val);
426 static void setup_row_direct_x(u8 temp, u8 source, u8 dest, u8 linkn)
431 val |= 1<<(linkn+1+8); /*for direct connect response route should equal to request table*/
433 if(((source &1)!=(dest &1))
435 && ( (source<4)||(source>5) ) //(6,7) (7,6) should still be here
436 //(6,5) (7,4) should be here
441 /*for CROSS_BAR_47_56 47, 56, should be here too
442 and for 47, 56, 57, 75, 46, 64 we need to substract another link to
445 val_s = get_row(temp, source);
446 val |= ((val_s>>16) - (1<<(linkn+1)))<<16;
449 fill_row(temp,dest, val );
453 static void opt_broadcast_rt(u8 source, u8 dest, u8 kickout)
456 val = get_row(source, dest);
457 val -= link_connection(source, kickout)<<16;
458 fill_row(source, dest, val);
461 static void opt_broadcast_rt_group(const u8 *conn, int num)
465 for(i=0; i<num; i+=3) {
466 opt_broadcast_rt(conn[i], conn[i+1],conn[i+2]);
470 static void opt_broadcast_rt_plus(u8 source, u8 dest, u8 kickout)
473 val = get_row(source, dest);
474 val += link_connection(source, kickout)<<16;
475 fill_row(source, dest, val);
478 static void opt_broadcast_rt_plus_group(const u8 *conn, int num)
482 for(i=0; i<num; i+=3) {
483 opt_broadcast_rt_plus(conn[i], conn[i+1],conn[i+2]);
488 static void setup_row_direct(u8 source, u8 dest, u8 linkn)
490 setup_row_direct_x(source, source, dest, linkn);
493 static void setup_remote_row_direct(u8 source, u8 dest, u8 linkn)
495 setup_row_direct_x(7, source, dest, linkn);
498 static void setup_temp_row(u8 source, u8 dest)
500 /* copy value from (source, dest) to (source,7) */
501 fill_row(source, 7, get_row(source, dest));
504 static void setup_remote_node(u8 node)
506 static const uint8_t pci_reg[] = {
507 0x44, 0x4c, 0x54, 0x5c, 0x64, 0x6c, 0x74, 0x7c,
508 0x40, 0x48, 0x50, 0x58, 0x60, 0x68, 0x70, 0x78,
509 0x84, 0x8c, 0x94, 0x9c, 0xa4, 0xac, 0xb4, 0xbc,
510 0x80, 0x88, 0x90, 0x98, 0xa0, 0xa8, 0xb0, 0xb8,
511 0xc4, 0xcc, 0xd4, 0xdc,
512 0xc0, 0xc8, 0xd0, 0xd8,
513 0xe0, 0xe4, 0xe8, 0xec,
517 print_spew("setup_remote_node: ");
519 /* copy the default resource map from node 0 */
520 for(i = 0; i < ARRAY_SIZE(pci_reg); i++) {
524 value = pci_read_config32(NODE_MP(0), reg);
525 pci_write_config32(NODE_MP(7), reg, value);
528 print_spew("done\n");
531 #endif /* CONFIG_MAX_PHYSICAL_CPUS > 1*/
534 #if CONFIG_MAX_PHYSICAL_CPUS > 2
536 static void setup_row_indirect_x(u8 temp, u8 source, u8 dest)
538 static void setup_row_indirect_x(u8 temp, u8 source, u8 dest, u8 gateway, u8 diff)
541 /*for indirect connection, we need to compute the val from val_s(source, source), and val_g(source, gateway) */
548 gateway = source + 2;
550 gateway = source - 2;
553 val_s = get_row(temp, source);
554 val = get_row(temp, gateway);
561 diff = ((source&1)!=(dest &1));
564 if(diff && (val_s!=(val&0xff)) ) { /* use another connect as response*/
566 #if (CONFIG_MAX_PHYSICAL_CPUS > 4) || (CONFIG_MAX_PHYSICAL_CPUS_4_BUT_MORE_INSTALLED == 1)
568 /* Some node have two links left
569 * don't worry we only have (2, (3 as source need to handle
572 byte = get_linkn_last_count(byte);
573 if((byte>>2)>1) { /* make sure not the corner*/
575 val_s-=link_connection(temp, source-2); /* -down*/
580 val_s-=link_connection(temp, 6); // for 7,2 via 5
581 } else if (source==6){
582 val_s-=link_connection(temp, 7); // for 6,3 via 4
585 if (source < gateway) { // for 5, 4 via 7
586 val_s-=link_connection(temp, source-2);
589 val_s-=link_connection(temp, source+2); /* -up*/
597 if(diff) { /* cross rung?*/
601 val_s = get_row(temp, source);
602 val |= ((val_s>>16) - link_connection(temp, gateway))<<16;
605 fill_row(temp, dest, val);
610 static void setup_row_indirect(u8 source, u8 dest)
612 setup_row_indirect_x(source, source, dest);
615 static void setup_row_indirect(u8 source, u8 dest, u8 gateway, u8 diff)
617 setup_row_indirect_x(source, source, dest, gateway, diff);
621 static void setup_row_indirect_group(const u8 *conn, int num)
626 for(i=0; i<num; i+=2) {
627 setup_row_indirect(conn[i], conn[i+1]);
629 for(i=0; i<num; i+=4) {
630 setup_row_indirect(conn[i], conn[i+1],conn[i+2], conn[i+3]);
637 static void setup_remote_row_indirect(u8 source, u8 dest)
639 setup_row_indirect_x(7, source, dest);
642 static void setup_remote_row_indirect(u8 source, u8 dest, u8 gateway, u8 diff)
644 setup_row_indirect_x(7, source, dest, gateway, diff);
648 static void setup_remote_row_indirect_group(const u8 *conn, int num)
653 for(i=0; i<num; i+=2) {
654 setup_remote_row_indirect(conn[i], conn[i+1]);
656 for(i=0; i<num; i+=4) {
657 setup_remote_row_indirect(conn[i], conn[i+1],conn[i+2], conn[i+3]);
662 #endif /*CONFIG_MAX_PHYSICAL_CPUS > 2*/
665 static void setup_uniprocessor(void)
667 print_spew("Enabling UP settings\n");
668 #if CONFIG_LOGICAL_CPUS==1
669 unsigned tmp = (pci_read_config32(NODE_MC(0), 0xe8) >> 12) & 3;
675 #if CONFIG_MAX_PHYSICAL_CPUS > 2
676 static int optimize_connection_group(const u8 *opt_conn, int num)
680 for(i=0; i<num; i+=2) {
681 needs_reset = optimize_connection(
682 NODE_HT(opt_conn[i]), 0x80 + link_to_register(link_connection(opt_conn[i],opt_conn[i+1])),
683 NODE_HT(opt_conn[i+1]), 0x80 + link_to_register(link_connection(opt_conn[i+1],opt_conn[i])) );
689 #if CONFIG_MAX_PHYSICAL_CPUS > 1
690 static unsigned setup_smp2(void)
697 setup_row_local(0, 0); /* it will update the broadcast RT*/
700 byte = (val>>16) & 0xfe;
701 if(byte<0x2) { /* no coherent connection so get out.*/
706 /* Setup and check a temporary connection to node 1 */
707 #if TRY_HIGH_FIRST == 1
708 byte = get_linkn_last(byte); /* Max Link to node1 */
710 byte = get_linkn_first(byte); /*Min Link to node1 --- according to AMD*/
712 print_linkn("(0,1) link=", byte);
713 setup_row_direct(0,1, byte);
714 setup_temp_row(0, 1);
716 verify_connection(7);
718 /* We found 2 nodes so far */
719 val = pci_read_config32(NODE_HT(7), 0x6c);
720 byte = (val>>2) & 0x3; /*get default link on node7 to node0*/
721 print_linkn("(1,0) link=", byte);
722 setup_row_local(7,1);
723 setup_remote_row_direct(1, 0, byte);
725 #if (CONFIG_MAX_PHYSICAL_CPUS > 4) || (CONFIG_MAX_PHYSICAL_CPUS_4_BUT_MORE_INSTALLED == 1)
727 byte = (val>>16) & 0xfe;
728 byte = get_linkn_last_count(byte);
729 if((byte>>2)==3) { /* Oh! we need to treat it as node2. So use another link*/
731 byte = (val>>16) & 0xfe;
732 #if TRY_HIGH_FIRST == 1
733 byte = get_linkn_first(byte); /* Min link to Node1 */
735 byte = get_linkn_last(byte); /* Max link to Node1*/
737 print_linkn("\t-->(0,1) link=", byte);
738 setup_row_direct(0,1, byte);
739 setup_temp_row(0, 1);
741 verify_connection(7);
743 /* We found 2 nodes so far */
744 val = pci_read_config32(NODE_HT(7), 0x6c);
745 byte = (val>>2) & 0x3; /* get default link on node7 to node0*/
746 print_linkn("\t-->(1,0) link=", byte);
747 setup_row_local(7,1);
748 setup_remote_row_direct(1, 0, byte);
752 setup_remote_node(1); /* Setup the regs on the remote node */
753 rename_temp_node(1); /* Rename Node 7 to Node 1 */
754 enable_routing(1); /* Enable routing on Node 1 */
756 /*don't need and it is done by clear_dead_links */
762 #endif /*CONFIG_MAX_PHYSICAL_CPUS > 1 */
764 #if CONFIG_MAX_PHYSICAL_CPUS > 2
766 static unsigned setup_smp4(void)
774 /* Setup and check temporary connection from Node 0 to Node 2 */
776 byte = ((val>>16) & 0xfe) - link_connection(0,1);
777 byte = get_linkn_last_count(byte);
779 if((byte>>2)==0) { /* We should have two coherent for 4p and above*/
784 byte &= 3; /* bit [3,2] is count-1*/
785 print_linkn("(0,2) link=", byte);
786 setup_row_direct(0, 2, byte); /*(0,2) direct link done*/
788 /* We found 3 nodes so far. Now setup a temporary
789 * connection from node 0 to node 3 via node 1
791 setup_temp_row(0,1); /* temp. link between nodes 0 and 1 */
792 /* here should setup_row_direct(1,3) at first, before that we should find the link in node 1 to 3*/
794 byte = ((val>>16) & 0xfe) - link_connection(1,0);
795 byte = get_linkn_first(byte);
796 print_linkn("(1,3) link=", byte);
797 setup_row_direct(1,3,byte); /* (1, 3) direct link done*/
799 /* We found 4 nodes so far. Now setup all nodes for 4p */
800 // We need to make sure 0,2 and 1,3 link is set already
802 static const u8 conn4_1[] = {
807 static const u8 conn4_1[] = {
813 setup_row_indirect_group(conn4_1, ARRAY_SIZE(conn4_1));
816 verify_connection(7);
817 val = pci_read_config32(NODE_HT(7), 0x6c);
818 byte = (val>>2) & 0x3; /* get default link on 7 to 0*/
819 print_linkn("(2,0) link=", byte);
821 setup_row_local(7,2);
822 setup_remote_row_direct(2, 0, byte); /* node 2 to node 0 direct link done */
823 setup_remote_node(2); /* Setup the regs on the remote node */
825 rename_temp_node(2); /* Rename Node 7 to Node 2 */
826 enable_routing(2); /* Enable routing on Node 2 */
830 verify_connection(7);
832 val = pci_read_config32(NODE_HT(7), 0x6c);
833 byte = (val>>2) & 0x3; /* get default link on 7 to 1*/
834 print_linkn("(3,1) link=", byte);
836 setup_row_local(7,3);
837 setup_remote_row_direct(3, 1, byte); /* node 3 to node 1 direct link done */
838 setup_remote_node(3); /* Setup the regs on the remote node */
840 /* We need to init link between 2, and 3 direct link */
842 byte = ((val>>16) & 0xfe) - link_connection(2,0);
843 byte = get_linkn_last_count(byte);
844 print_linkn("(2,3) link=", byte & 3);
846 setup_row_direct(2,3, byte & 0x3);
849 verify_connection(7); /* to 3*/
851 #if (CONFIG_MAX_PHYSICAL_CPUS > 4) || (CONFIG_MAX_PHYSICAL_CPUS_4_BUT_MORE_INSTALLED == 1)
852 /* We need to find out which link is to node3 */
853 if((byte>>2)==2) { /* one to node3, one to node0, one to node4*/
855 if((val>>16) == 1) { /* that link is to node4, because via node1 it has been set, recompute it*/
857 byte = ((val>>16) & 0xfe) - link_connection(2,0);
858 byte = get_linkn_first(byte);
859 print_linkn("\t-->(2,3) link=", byte);
860 setup_row_direct(2,3,byte);
862 verify_connection(7); /* to 3*/
867 val = pci_read_config32(NODE_HT(7), 0x6c);
868 byte = (val>>2) & 0x3; /* get default link on 7 to 2*/
869 print_linkn("(3,2) link=", byte);
870 setup_remote_row_direct(3,2, byte);
872 #if (CONFIG_MAX_PHYSICAL_CPUS > 4) || (CONFIG_MAX_PHYSICAL_CPUS_4_BUT_MORE_INSTALLED == 1)
873 /* set link from 3 to 5 before enable it*/
875 byte = ((val>>16) & 0xfe) - link_connection(7,2) - link_connection(7,1);
876 byte = get_linkn_last_count(byte);
877 if((byte>>2)==1) { /* We should have three coherent links on node 3 for 6p and above*/
878 byte &= 3; /*bit [3,2] is count-2*/
879 print_linkn("(3,5) link=", byte);
880 setup_remote_row_direct(3, 5, byte);
884 byte = ((val>>16) & 0xfe) - link_connection(2,3) - link_connection(2,0);
885 byte = get_linkn_last_count(byte);
887 if((byte>>2)==1) { /* We should have three coherent link on node 2 for 6p and above*/
888 byte &= 3; /* bit [3,2] is count-2*/
889 print_linkn("(2,4) link=", byte);
890 setup_row_direct(2, 4, byte);
894 //Beside 3, 1 is set, We need to make sure 3, 5 is set already in case has three link in 3
896 static const u8 conn4_3[] = {
900 static const u8 conn4_3[] = {
904 setup_remote_row_indirect_group(conn4_3, ARRAY_SIZE(conn4_3));
906 /* ready to enable RT for Node 3 */
908 enable_routing(3); /* enable routing on node 3 (temp.) */
910 // beside 2, 0 is set, We need to make sure 2, 4 link is set already in case has three link in 2
912 static const u8 conn4_2[] = {
916 static const u8 conn4_2[] = {
920 setup_row_indirect_group(conn4_2, ARRAY_SIZE(conn4_2));
923 /*We need to do sth to reverse work for setup_temp_row (0,1) (1,3) */
924 /* it will be done by clear_dead_links */
933 #endif /* CONFIG_MAX_PHYSICAL_CPUS > 2 */
935 #if CONFIG_MAX_PHYSICAL_CPUS > 4
937 static unsigned setup_smp6(void)
945 /* Setup and check temporary connection from Node 0 to Node 4 through 2*/
947 byte = ((val>>16) & 0xfe) - link_connection(2,3) - link_connection(2,0);
948 byte = get_linkn_last_count(byte);
950 if((byte>>2)==0) { /* We should have three coherent link on node 2 for 6p and above*/
955 /* Setup and check temporary connection from Node 0 to Node 5 through 1, 3*/
956 /* set link from 3 to 5 before enable it*/
958 byte = ((val>>16) & 0xfe) - link_connection(3,2) - link_connection(3,1);
959 byte = get_linkn_last_count(byte);
960 if((byte>>2)==0) { /* We should have three coherent links on node 3 for 6p and above*/
965 /* We found 6 nodes so far. Now setup all nodes for 6p */
966 #warning "FIXME we need to find out the correct gateway for 6p"
967 static const u8 conn6_1[] = {
985 setup_row_indirect_group(conn6_1, ARRAY_SIZE(conn6_1));
987 for(byte=0; byte<4; byte+=2) {
988 setup_temp_row(byte,byte+2);
990 verify_connection(7);
991 val = pci_read_config32(NODE_HT(7), 0x6c);
992 byte = (val>>2) & 0x3; /*get default link on 7 to 2*/
993 print_linkn("(4,2) link=", byte);
995 setup_row_local(7,4);
996 setup_remote_row_direct(4, 2, byte);
997 setup_remote_node(4); /* Setup the regs on the remote node */
999 /* Set indirect connection to 0, to 3 */
1000 //we only need to set 4,0 here
1001 static const u8 conn6_2[] = {
1002 #if !CROSS_BAR_47_56
1009 setup_remote_row_indirect_group(conn6_2, ARRAY_SIZE(conn6_2));
1011 rename_temp_node(4);
1014 setup_temp_row(0,1);
1015 for(byte=0; byte<4; byte+=2) {
1016 setup_temp_row(byte+1,byte+3);
1018 verify_connection(7);
1020 val = pci_read_config32(NODE_HT(7), 0x6c);
1021 byte = (val>>2) & 0x3; /* get default link on 7 to 3*/
1022 print_linkn("(5,3) link=", byte);
1023 setup_row_local(7,5);
1024 setup_remote_row_direct(5, 3, byte);
1025 setup_remote_node(5); /* Setup the regs on the remote node */
1027 #if !CROSS_BAR_47_56
1028 /* We need to init link between 4, and 5 direct link */
1030 byte = ((val>>16) & 0xfe) - link_connection(4,2);
1031 byte = get_linkn_last_count(byte);
1032 print_linkn("(4,5) link=", byte & 3);
1034 setup_row_direct(4,5, byte & 0x3);
1035 setup_temp_row(0,2);
1036 setup_temp_row(2,4);
1037 setup_temp_row(4,5);
1038 verify_connection(7); /* to 5*/
1040 #if CONFIG_MAX_PHYSICAL_CPUS > 6
1041 /* We need to find out which link is to node5 */
1043 if((byte>>2)==2) { /* one to node5, one to node2, one to node6*/
1045 if((val>>16) == 1) { /* that link is to node6, because via node 3 node 5 has been set*/
1047 byte = ((val>>16) & 0xfe) - link_connection(4,2);
1048 byte = get_linkn_first(byte);
1049 print_linkn("\t-->(4,5) link=", byte);
1050 setup_row_direct(4,5,byte);
1051 setup_temp_row(4,5);
1052 verify_connection(7); /* to 5*/
1057 val = pci_read_config32(NODE_HT(7), 0x6c);
1058 byte = (val>>2) & 0x3; /* get default link on 7 to 4*/
1059 print_linkn("(5,4) link=", byte);
1060 setup_remote_row_direct(5,4, byte);
1064 byte = ((val>>16) & 0xfe) - link_connection(7,4) - link_connection(7,3);
1065 byte = get_linkn_last_count(byte);
1066 if((byte>>2)==1) { /* We should have three coherent links on node 5 for 6p and above*/
1067 byte &= 3; /*bit [3,2] is count-2*/
1068 print_linkn("(5,7) link=", byte);
1069 setup_remote_row_direct(5, 7, byte);
1074 byte = ((val>>16) & 0xfe) - link_connection(4,5) - link_connection(4,2);
1075 byte = get_linkn_last_count(byte);
1077 if((byte>>2)==1) { /* We should have three coherent link on node 4 for 6p and above*/
1078 byte &= 3; /* bit [3,2] is count-2*/
1079 print_linkn("(4,6) link=", byte);
1080 setup_row_direct(4, 6, byte);
1085 //We need to set 5,0 here only, We need to set up 5, 7 to make 5,0
1086 /* Set indirect connection to 0, to 3 for indirect we will use clockwise routing */
1087 static const u8 conn6_3[] = {
1088 #if !CROSS_BAR_47_56
1095 setup_remote_row_indirect_group(conn6_3, ARRAY_SIZE(conn6_3));
1097 /* ready to enable RT for 5 */
1098 rename_temp_node(5);
1099 enable_routing(5); /* enable routing on node 5 (temp.) */
1101 static const u8 conn6_4[] = {
1102 #if !CROSS_BAR_47_56
1121 setup_row_indirect_group(conn6_4, ARRAY_SIZE(conn6_4));
1124 /* We need to do sth about reverse about setup_temp_row (0,1), (2,4), (1, 3), (3,5)
1125 * It will be done by clear_dead_links
1127 for(byte=0; byte<4; byte++) {
1128 clear_temp_row(byte);
1136 #endif /* CONFIG_MAX_PHYSICAL_CPUS > 4 */
1138 #if CONFIG_MAX_PHYSICAL_CPUS > 6
1140 static unsigned setup_smp8(void)
1148 /* Setup and check temporary connection from Node 0 to Node 6 via 2 and 4 to 7 */
1151 byte = ((val>>16) & 0xfe) - link_connection(4,2);
1153 byte = ((val>>16) & 0xfe) - link_connection(4,5) - link_connection(4,2);
1154 byte = get_linkn_last_count(byte); /* Max link to 6*/
1155 if((byte>>2)==0) { /* We should have two or three coherent links on node 4 for 8p*/
1162 byte = get_linkn_last_count(byte); /* Max link to 6*/
1163 if((byte>>2)<2) { /* We should have two or three coherent links on node 4 for 8p*/
1167 #if TRY_HIGH_FIRST == 1
1168 byte = ((val>>16) & 0xfe) - link_connection(4,2);
1169 byte = get_linkn_first(byte); /*Min link to 6*/
1171 byte &= 3; /* bit [3,2] is count-1 or 2*/
1173 print_linkn("(4,6) link=", byte);
1174 setup_row_direct(4, 6, byte);
1177 #if !CROSS_BAR_47_56
1178 /* Setup and check temporary connection from Node 0 to Node 7 through 1, 3, 5*/
1180 byte = ((val>>16) & 0xfe) - link_connection(5,4) - link_connection(5,3);
1181 byte = get_linkn_last_count(byte);
1182 if((byte>>2)==0) { /* We should have three coherent links on node 5 for 6p and above*/
1188 /* We found 8 nodes so far. Now setup all nodes for 8p */
1189 static const u8 conn8_1[] = {
1190 #if !CROSS_BAR_47_56
1213 setup_row_indirect_group(conn8_1,ARRAY_SIZE(conn8_1));
1215 for(byte=0; byte<6; byte+=2) {
1216 setup_temp_row(byte,byte+2);
1218 verify_connection(7);
1219 val = pci_read_config32(NODE_HT(7), 0x6c);
1220 byte = (val>>2) & 0x3; /* get default link on 7 to 4*/
1221 print_linkn("(6,4) link=", byte);
1223 setup_row_local(7,6);
1224 setup_remote_row_direct(6, 4, byte);
1225 setup_remote_node(6); /* Setup the regs on the remote node */
1226 /* Set indirect connection to 0, to 3 */
1227 #warning "FIXME we need to find out the correct gateway for 8p"
1228 static const u8 conn8_2[] = {
1229 #if !CROSS_BAR_47_56
1236 setup_remote_row_indirect_group(conn8_2, ARRAY_SIZE(conn8_2));
1240 /* here init 5, 6 */
1241 /* Setup and check temporary connection from Node 0 to Node 5 through 1, 3, 5*/
1243 byte = ((val>>16) & 0xfe) - link_connection(5,3);
1244 #if TRY_HIGH_FIRST == 1
1245 byte = get_linkn_first(byte);
1247 byte = get_linkn_last(byte);
1249 print_linkn("(5,6) link=", byte);
1250 setup_row_direct(5, 6, byte);
1252 setup_temp_row(0,1); /* temp. link between nodes 0 and 1 */
1253 for(byte=0; byte<4; byte+=2) {
1254 setup_temp_row(byte+1,byte+3);
1256 setup_temp_row(5,6);
1258 verify_connection(7);
1260 val = get_row(7,6); // to chect it if it is node6 before renaming
1261 if( (val>>16) == 1) { // it is real node 7 so swap it
1262 /* We need to recompute link to 6 */
1264 byte = ((val>>16) & 0xfe) - link_connection(5,3);
1265 #if TRY_HIGH_FIRST == 1
1266 byte = get_linkn_first(byte);
1268 byte = get_linkn_last(byte);
1270 print_linkn("\t-->(5,6) link=", byte);
1271 setup_row_direct(5, 6, byte);
1273 setup_temp_row(0,1); /* temp. link between nodes 0 and 1 */
1274 for(byte=0; byte<4; byte+=2) {
1275 setup_temp_row(byte+1,byte+3);
1278 setup_temp_row(5,6);
1280 verify_connection(7);
1282 val = pci_read_config32(NODE_HT(7), 0x6c);
1283 byte = (val>>2) & 0x3; /* get default link on 7 to 5*/
1284 print_linkn("(6,5) link=", byte);
1285 setup_remote_row_direct(6, 5, byte);
1286 /*Till now 56, 65 done */
1289 rename_temp_node(6);
1292 #if !CROSS_BAR_47_56
1293 setup_temp_row(0,1);
1294 for(byte=0; byte<6; byte+=2) {
1295 setup_temp_row(byte+1,byte+3);
1298 verify_connection(7);
1300 val = pci_read_config32(NODE_HT(7), 0x6c);
1301 byte = (val>>2) & 0x3; /* get default link on 7 to 5*/
1302 print_linkn("(7,5) link=", byte);
1303 setup_row_local(7,7);
1304 setup_remote_row_direct(7, 5, byte);
1308 byte = ((val>>16) & 0xfe) - link_connection(4,2) - link_connection(4,6);
1309 byte = get_linkn_first(byte);
1310 print_linkn("(4,7) link=", byte);
1311 setup_row_direct(4, 7, byte);
1313 /* Setup and check temporary connection from Node 0 to Node 7 through 2, and 4*/
1314 for(byte=0; byte<4; byte+=2) {
1315 setup_temp_row(byte,byte+2);
1318 verify_connection(7);
1320 val = pci_read_config32(NODE_HT(7), 0x6c);
1321 byte = (val>>2) & 0x3; /* get default link on 7 to 4*/
1322 print_linkn("(7,4) link=", byte);
1323 setup_row_local(7,7);
1324 setup_remote_row_direct(7, 4, byte);
1325 /* till now 4-7, 7-4 done. */
1327 setup_remote_node(7); /* Setup the regs on the remote node */
1330 /* here init 5, 7 */
1331 /* Setup and check temporary connection from Node 0 to Node 5 through 1, 3, 5*/
1333 byte = ((val>>16) & 0xfe) - link_connection(5,3) - link_connection(5,6);
1334 byte = get_linkn_first(byte);
1335 print_linkn("(5,7) link=", byte);
1336 setup_row_direct(5, 7, byte);
1338 setup_temp_row(0,1); /* temp. link between nodes 0 and 1 */
1339 for(byte=0; byte<4; byte+=2) {
1340 setup_temp_row(byte+1,byte+3);
1343 verify_connection(7);
1345 val = pci_read_config32(NODE_HT(7), 0x6c);
1346 byte = (val>>2) & 0x3; /* get default link on 7 to 5*/
1347 print_linkn("(7,5) link=", byte);
1348 setup_remote_row_direct(7, 5, byte);
1349 /*Till now 57, 75 done */
1353 /* We need to init link between 6, and 7 direct link */
1355 #if !CROSS_BAR_47_56
1356 byte = ((val>>16) & 0xfe) - link_connection(6,4);
1358 byte = ((val>>16) & 0xfe) - link_connection(6,4) - link_connection(6,5);
1360 byte = get_linkn_first(byte);
1361 print_linkn("(6,7) link=", byte);
1362 setup_row_direct(6,7, byte);
1365 #if !CROSS_BAR_47_56
1366 byte = ((val>>16) & 0xfe) - link_connection(7,5);
1368 byte = ((val>>16) & 0xfe) - link_connection(7,5) - link_connection(7,4);
1370 byte = get_linkn_first(byte);
1371 print_linkn("(7,6) link=", byte);
1372 setup_row_direct(7,6, byte);
1374 /* Set indirect connection to 0, to 3 for indirect we will use clockwise routing */
1375 static const u8 conn8_3[] = {
1376 #if !CROSS_BAR_47_56
1377 0, 7, /* restore it*/
1399 6, 1, 5, 0, // or 4, 1
1401 6, 3, 5, 0, // or 4, 1
1403 7, 0, 4, 0, // or 5, 1
1405 7, 2, 4, 0, // or 5, 1
1408 0, 7, 2, 0, /* restore it*/
1413 2, 5, 4, 1, /* reset it */
1416 4, 1, 2, 1, /* reset it */
1419 5, 2, 3, 1, /* reset it */
1425 setup_row_indirect_group(conn8_3, ARRAY_SIZE(conn8_3));
1428 /* for 47, 56, 57, 75, 46, 64 we need to substract another link to
1430 static const u8 conn8_4[] = {
1453 6, 1, 7, // needed for via 5
1456 6, 3, 7, // needed for via 5
1458 7, 0, 6, // needed for via 4
1461 7, 2, 6, // needed for via 4
1466 opt_broadcast_rt_group(conn8_4, ARRAY_SIZE(conn8_4));
1468 static const u8 conn8_5[] = {
1474 opt_broadcast_rt_plus_group(conn8_5, ARRAY_SIZE(conn8_5));
1479 /* ready to enable RT for Node 7 */
1480 enable_routing(7); /* enable routing on node 7 (temp.) */
1485 #endif /* CONFIG_MAX_PHYSICAL_CPUS > 6 */
1488 #if CONFIG_MAX_PHYSICAL_CPUS > 1
1490 static unsigned setup_smp(void)
1494 print_spew("Enabling SMP settings\n");
1496 nodes = setup_smp2();
1497 #if CONFIG_MAX_PHYSICAL_CPUS > 2
1499 nodes = setup_smp4();
1502 #if CONFIG_MAX_PHYSICAL_CPUS > 4
1504 nodes = setup_smp6();
1507 #if CONFIG_MAX_PHYSICAL_CPUS > 6
1509 nodes = setup_smp8();
1512 printk(BIOS_DEBUG, "%02x nodes initialized.\n", nodes);
1517 static unsigned verify_mp_capabilities(unsigned nodes)
1519 unsigned node, mask;
1521 mask = 0x06; /* BigMPCap */
1523 for (node=0; node<nodes; node++) {
1524 mask &= pci_read_config32(NODE_MC(node), 0xe8);
1528 #if CONFIG_MAX_PHYSICAL_CPUS > 2
1529 case 0x02: /* MPCap */
1531 print_err("Going back to DP\n");
1536 case 0x00: /* Non SMP */
1538 print_err("Going back to UP\n");
1549 static void clear_dead_routes(unsigned nodes)
1553 #if CONFIG_MAX_PHYSICAL_CPUS == 8
1554 if(nodes==8) return;/* don't touch (7,7)*/
1560 for(node = 7; node >= 0; node--) {
1561 for(row = 7; row >= last_row; row--) {
1562 fill_row(node, row, DEFAULT);
1566 /* Update the local row */
1567 for( node=0; node<nodes; node++) {
1569 for(row =0; row<nodes; row++) {
1570 val |= get_row(node, row);
1572 fill_row(node, node, (((val & 0xff) | ((val >> 8) & 0xff)) << 16) | 0x0101);
1575 #endif /* CONFIG_MAX_PHYSICAL_CPUS > 1 */
1577 #if CONFIG_LOGICAL_CPUS==1
1578 static unsigned verify_dualcore(unsigned nodes)
1580 unsigned node, totalcpus, tmp;
1583 for (node=0; node<nodes; node++) {
1584 tmp = (pci_read_config32(NODE_MC(node), 0xe8) >> 12) & 3 ;
1585 totalcpus += (tmp + 1);
1593 static void coherent_ht_finalize(unsigned nodes)
1596 #if CONFIG_K8_REV_F_SUPPORT == 0
1599 #if CONFIG_LOGICAL_CPUS==1
1600 unsigned total_cpus;
1602 if (read_option(multi_core, 0) == 0) { /* multi_core */
1603 total_cpus = verify_dualcore(nodes);
1610 /* set up cpu count and node count and enable Limit
1611 * Config Space Range for all available CPUs.
1612 * Also clear non coherent hypertransport bus range
1613 * registers on Hammer A0 revision.
1616 print_spew("coherent_ht_finalize\n");
1617 #if CONFIG_K8_REV_F_SUPPORT == 0
1618 rev_a0 = is_cpu_rev_a0();
1620 for (node = 0; node < nodes; node++) {
1623 dev = NODE_HT(node);
1625 /* Set the Total CPU and Node count in the system */
1626 val = pci_read_config32(dev, 0x60);
1627 val &= (~0x000F0070);
1628 #if CONFIG_LOGICAL_CPUS==1
1629 val |= ((total_cpus-1)<<16)|((nodes-1)<<4);
1631 val |= ((nodes-1)<<16)|((nodes-1)<<4);
1633 pci_write_config32(dev, 0x60, val);
1635 /* Only respond to real cpu pci configuration cycles
1636 * and optimize the HT settings
1638 val=pci_read_config32(dev, HT_TRANSACTION_CONTROL);
1639 val &= ~((HTTC_BUF_REL_PRI_MASK << HTTC_BUF_REL_PRI_SHIFT) |
1640 (HTTC_MED_PRI_BYP_CNT_MASK << HTTC_MED_PRI_BYP_CNT_SHIFT) |
1641 (HTTC_HI_PRI_BYP_CNT_MASK << HTTC_HI_PRI_BYP_CNT_SHIFT));
1642 val |= HTTC_LIMIT_CLDT_CFG |
1643 (HTTC_BUF_REL_PRI_8 << HTTC_BUF_REL_PRI_SHIFT) |
1644 (3 << HTTC_MED_PRI_BYP_CNT_SHIFT) |
1645 (3 << HTTC_HI_PRI_BYP_CNT_SHIFT);
1646 pci_write_config32(dev, HT_TRANSACTION_CONTROL, val);
1648 #if CONFIG_K8_REV_F_SUPPORT == 0
1650 pci_write_config32(dev, 0x94, 0);
1651 pci_write_config32(dev, 0xb4, 0);
1652 pci_write_config32(dev, 0xd4, 0);
1657 print_spew("done\n");
1660 static int apply_cpu_errata_fixes(unsigned nodes)
1663 int needs_reset = 0;
1664 for(node = 0; node < nodes; node++) {
1667 dev = NODE_MC(node);
1668 #if CONFIG_K8_REV_F_SUPPORT == 0
1669 if (is_cpu_pre_c0()) {
1672 * Limit the number of downstream posted requests to 1
1674 cmd = pci_read_config32(dev, 0x70);
1675 if ((cmd & (3 << 0)) != 2) {
1678 pci_write_config32(dev, 0x70, cmd );
1681 cmd = pci_read_config32(dev, 0x7c);
1682 if ((cmd & (3 << 4)) != 0) {
1685 pci_write_config32(dev, 0x7c, cmd );
1688 /* Clock Power/Timing Low */
1689 cmd = pci_read_config32(dev, 0xd4);
1690 if (cmd != 0x000D0001) {
1692 pci_write_config32(dev, 0xd4, cmd);
1693 needs_reset = 1; /* Needed? */
1697 else if (is_cpu_pre_d0()) { // d0 later don't need it
1700 * Set Clk Ramp Hystersis to 7
1701 * Clock Power/Timing Low
1703 cmd_ref = 0x04e20707; /* Registered */
1704 cmd = pci_read_config32(dev, 0xd4);
1705 if(cmd != cmd_ref) {
1706 pci_write_config32(dev, 0xd4, cmd_ref );
1707 needs_reset = 1; /* Needed? */
1713 #if CONFIG_K8_REV_F_SUPPORT == 0
1714 /* I can't touch this msr on early buggy cpus, and cannot apply either 169 or 131 */
1715 if (!is_cpu_pre_b3())
1719 /* We also need to set some bits in NB_CFG_MSR, which is handled in src/cpu/amd/model_fxx/ */
1720 dev = NODE_HT(node);
1721 cmd = pci_read_config32(dev, 0x68);
1724 pci_write_config32(dev, 0x68, cmd);
1730 static int optimize_link_read_pointers(unsigned nodes)
1733 int needs_reset = 0;
1734 for(node = 0; node < nodes; node++) {
1735 device_t f0_dev, f3_dev;
1736 uint32_t cmd_ref, cmd;
1738 f0_dev = NODE_HT(node);
1739 f3_dev = NODE_MC(node);
1740 cmd_ref = cmd = pci_read_config32(f3_dev, 0xdc);
1741 for(link = 0; link < 3; link++) {
1744 /* This works on an Athlon64 because unimplemented links return 0 */
1745 reg = 0x98 + (link * 0x20);
1746 link_type = pci_read_config32(f0_dev, reg);
1747 /* Only handle coherent links */
1748 if ((link_type & (LinkConnected | InitComplete|NonCoherent)) ==
1749 (LinkConnected|InitComplete))
1751 cmd &= ~(0xff << (link *8));
1752 cmd |= 0x25 << (link *8);
1755 if (cmd != cmd_ref) {
1756 pci_write_config32(f3_dev, 0xdc, cmd);
1763 static inline unsigned get_nodes(void)
1765 return ((pci_read_config32(PCI_DEV(0, 0x18, 0), 0x60)>>4) & 7) + 1;
1768 static int optimize_link_coherent_ht(void)
1770 int needs_reset = 0;
1774 nodes = get_nodes();
1776 #if CONFIG_MAX_PHYSICAL_CPUS > 1
1778 needs_reset |= optimize_connection(
1779 NODE_HT(0), 0x80 + link_to_register(link_connection(0,1)),
1780 NODE_HT(1), 0x80 + link_to_register(link_connection(1,0)) );
1783 #if CONFIG_MAX_PHYSICAL_CPUS > 2
1785 /* optimize physical connections - by LYH */
1786 static const u8 opt_conn4[] = {
1791 needs_reset |= optimize_connection_group(opt_conn4, ARRAY_SIZE(opt_conn4));
1795 #if CONFIG_MAX_PHYSICAL_CPUS > 4
1797 static const uint8_t opt_conn6[] ={
1800 #if !CROSS_BAR_47_56
1804 needs_reset |= optimize_connection_group(opt_conn6, ARRAY_SIZE(opt_conn6));
1808 #if CONFIG_MAX_PHYSICAL_CPUS > 6
1810 static const uint8_t opt_conn8[] ={
1819 needs_reset |= optimize_connection_group(opt_conn8, ARRAY_SIZE(opt_conn8));
1825 needs_reset |= apply_cpu_errata_fixes(nodes);
1826 needs_reset |= optimize_link_read_pointers(nodes);
1831 #if CONFIG_RAMINIT_SYSINFO
1832 static void setup_coherent_ht_domain(void)
1834 static int setup_coherent_ht_domain(void)
1840 enable_bsp_routing();
1842 #if CONFIG_MAX_PHYSICAL_CPUS > 1
1843 nodes = setup_smp();
1844 nodes = verify_mp_capabilities(nodes);
1845 clear_dead_routes(nodes);
1849 setup_uniprocessor();
1851 coherent_ht_finalize(nodes);
1853 #if !CONFIG_RAMINIT_SYSINFO
1854 return optimize_link_coherent_ht();