de5bfd537b3a0f97dc962c572bef5d16e5197908
[coreboot.git] / src / northbridge / amd / amdk8 / incoherent_ht.c
1 /*
2         This should be done by Eric
3         2004.12 yhlu add multi ht chain dynamically support
4         2005.11 yhlu add let real sb to use small unitid
5 */
6 #include <device/pci_def.h>
7 #include <device/pci_ids.h>
8 #include <device/hypertransport_def.h>
9
10 #ifndef K8_HT_FREQ_1G_SUPPORT
11         #define K8_HT_FREQ_1G_SUPPORT 0
12 #endif
13
14 #ifndef K8_SCAN_PCI_BUS
15         #define K8_SCAN_PCI_BUS 0
16 #endif
17
18 #ifndef K8_ALLOCATE_IO_RANGE
19         #define K8_ALLOCATE_IO_RANGE 0
20 #endif
21
22 // Do we need allocate MMIO? Current We direct last 64M to sblink only, We can not lose access to last 4M range to ROM 
23 #ifndef K8_ALLOCATE_MMIO_RANGE
24         #define K8_ALLOCATE_MMIO_RANGE 0
25 #endif
26
27 static inline void print_linkn_in (const char *strval, uint8_t byteval)
28 {
29 #if CONFIG_USE_PRINTK_IN_CAR
30         printk_debug("%s%02x\r\n", strval, byteval); 
31 #else
32         print_debug(strval); print_debug_hex8(byteval); print_debug("\r\n");
33 #endif
34 }
35
36 static uint8_t ht_lookup_capability(device_t dev, uint16_t val)
37 {
38         uint8_t pos;
39         uint8_t hdr_type;
40
41         hdr_type = pci_read_config8(dev, PCI_HEADER_TYPE);
42         pos = 0;
43         hdr_type &= 0x7f;
44
45         if ((hdr_type == PCI_HEADER_TYPE_NORMAL) ||
46             (hdr_type == PCI_HEADER_TYPE_BRIDGE)) {
47                 pos = PCI_CAPABILITY_LIST;
48         }
49         if (pos > PCI_CAP_LIST_NEXT) {
50                 pos = pci_read_config8(dev, pos);
51         }
52         while(pos != 0) { /* loop through the linked list */
53                 uint8_t cap;
54                 cap = pci_read_config8(dev, pos + PCI_CAP_LIST_ID);
55                 if (cap == PCI_CAP_ID_HT) {
56                         uint16_t flags;
57
58                         flags = pci_read_config16(dev, pos + PCI_CAP_FLAGS);
59                         if ((flags >> 13) == val) {
60                                 /* Entry is a slave or host , success... */
61                                 break;
62                         }
63                 }
64                 pos = pci_read_config8(dev, pos + PCI_CAP_LIST_NEXT);
65         }
66         return pos;
67 }
68
69 static uint8_t ht_lookup_slave_capability(device_t dev)
70 {          
71         return ht_lookup_capability(dev, 0); // Slave/Primary Interface Block Format
72 }
73
74 static uint8_t ht_lookup_host_capability(device_t dev)
75 {
76         return ht_lookup_capability(dev, 1); // Host/Secondary Interface Block Format
77 }
78
79 static void ht_collapse_previous_enumeration(uint8_t bus, unsigned offset_unitid)
80 {
81         device_t dev;
82         uint32_t id;
83
84         //actually, only for one HT device HT chain, and unitid is 0
85 #if HT_CHAIN_UNITID_BASE == 0
86         if(offset_unitid) {
87                 return;
88         }
89 #endif
90
91         /* Check if is already collapsed */
92         if((!offset_unitid) || (offset_unitid && (!((HT_CHAIN_END_UNITID_BASE == 0) && (HT_CHAIN_END_UNITID_BASE <HT_CHAIN_UNITID_BASE))))) {
93                 dev = PCI_DEV(bus, 0, 0);
94                 id = pci_read_config32(dev, PCI_VENDOR_ID);
95                 if ( ! ( (id == 0xffffffff) || (id == 0x00000000) ||
96                     (id == 0x0000ffff) || (id == 0xffff0000) ) ) {
97                              return;
98                 }
99         } 
100
101         /* Spin through the devices and collapse any previous
102          * hypertransport enumeration.
103          */
104         for(dev = PCI_DEV(bus, 1, 0); dev <= PCI_DEV(bus, 0x1f, 0x7); dev += PCI_DEV(0, 1, 0)) {
105                 uint32_t id;
106                 uint8_t pos;
107                 uint16_t flags;
108                 
109                 id = pci_read_config32(dev, PCI_VENDOR_ID);
110                 if ((id == 0xffffffff) || (id == 0x00000000) ||
111                     (id == 0x0000ffff) || (id == 0xffff0000)) {
112                         continue;
113                 }
114                 
115                 pos = ht_lookup_slave_capability(dev);
116                 if (!pos) {
117                         continue;
118                 }
119
120                 /* Clear the unitid */
121                 flags = pci_read_config16(dev, pos + PCI_CAP_FLAGS);
122                 flags &= ~0x1f;
123                 pci_write_config16(dev, pos + PCI_CAP_FLAGS, flags);
124         }
125 }
126
127 static uint16_t ht_read_freq_cap(device_t dev, uint8_t pos)
128 {
129         /* Handle bugs in valid hypertransport frequency reporting */
130         uint16_t freq_cap;
131         uint32_t id;
132
133         freq_cap = pci_read_config16(dev, pos);
134         freq_cap &= ~(1 << HT_FREQ_VENDOR); /* Ignore Vendor HT frequencies */
135
136         id = pci_read_config32(dev, 0);
137
138         /* AMD 8131 Errata 48 */
139         if (id == (PCI_VENDOR_ID_AMD | (PCI_DEVICE_ID_AMD_8131_PCIX << 16))) {
140                 freq_cap &= ~(1 << HT_FREQ_800Mhz);
141                 return freq_cap;
142         }
143
144         /* AMD 8151 Errata 23 */
145         if (id == (PCI_VENDOR_ID_AMD | (PCI_DEVICE_ID_AMD_8151_SYSCTRL << 16))) {
146                 freq_cap &= ~(1 << HT_FREQ_800Mhz);
147                 return freq_cap;
148         } 
149         
150         /* AMD K8 Unsupported 1Ghz? */
151         if (id == (PCI_VENDOR_ID_AMD | (0x1100 << 16))) {
152         #if K8_HT_FREQ_1G_SUPPORT == 1 
153                 #if K8_REV_F_SUPPORT == 0 
154                 if (is_cpu_pre_e0()) {  // only E0 later support 1GHz
155                         freq_cap &= ~(1 << HT_FREQ_1000Mhz);
156                 }
157                 #endif
158         #else   
159                 freq_cap &= ~(1 << HT_FREQ_1000Mhz);
160         #endif
161         }
162
163         return freq_cap;
164 }
165 #define LINK_OFFS(CTRL, WIDTH,FREQ,FREQ_CAP) \
166       (((CTRL & 0xff) << 24) | ((WIDTH & 0xff) << 16) | ((FREQ & 0xff) << 8) | (FREQ_CAP & 0xFF))
167
168 #define LINK_CTRL(OFFS)     ((OFFS >> 24) & 0xFF)
169 #define LINK_WIDTH(OFFS)    ((OFFS >> 16) & 0xFF)
170 #define LINK_FREQ(OFFS)     ((OFFS >> 8) & 0xFF)
171 #define LINK_FREQ_CAP(OFFS) ((OFFS) & 0xFF)
172
173 #define PCI_HT_HOST_OFFS LINK_OFFS(             \
174                 PCI_HT_CAP_HOST_CTRL,           \
175                 PCI_HT_CAP_HOST_WIDTH,          \
176                 PCI_HT_CAP_HOST_FREQ,           \
177                 PCI_HT_CAP_HOST_FREQ_CAP)
178
179 #define PCI_HT_SLAVE0_OFFS LINK_OFFS(           \
180                 PCI_HT_CAP_SLAVE_CTRL0,         \
181                 PCI_HT_CAP_SLAVE_WIDTH0,        \
182                 PCI_HT_CAP_SLAVE_FREQ0,         \
183                 PCI_HT_CAP_SLAVE_FREQ_CAP0)
184
185 #define PCI_HT_SLAVE1_OFFS LINK_OFFS(           \
186                 PCI_HT_CAP_SLAVE_CTRL1,         \
187                 PCI_HT_CAP_SLAVE_WIDTH1,        \
188                 PCI_HT_CAP_SLAVE_FREQ1,         \
189                 PCI_HT_CAP_SLAVE_FREQ_CAP1)
190
191 static int ht_optimize_link(
192         device_t dev1, uint8_t pos1, unsigned offs1,
193         device_t dev2, uint8_t pos2, unsigned offs2)
194 {
195         static const uint8_t link_width_to_pow2[]= { 3, 4, 0, 5, 1, 2, 0, 0 };
196         static const uint8_t pow2_to_link_width[] = { 0x7, 4, 5, 0, 1, 3 };
197         uint16_t freq_cap1, freq_cap2;
198         uint8_t width_cap1, width_cap2, width, old_width, ln_width1, ln_width2;
199         uint8_t freq, old_freq;
200         int needs_reset;
201         /* Set link width and frequency */
202
203         /* Initially assume everything is already optimized and I don't need a reset */
204         needs_reset = 0;
205
206         /* Get the frequency capabilities */
207         freq_cap1 = ht_read_freq_cap(dev1, pos1 + LINK_FREQ_CAP(offs1));
208         freq_cap2 = ht_read_freq_cap(dev2, pos2 + LINK_FREQ_CAP(offs2));
209
210         /* Calculate the highest possible frequency */
211         freq = log2(freq_cap1 & freq_cap2);
212
213         /* See if I am changing the link freqency */
214         old_freq = pci_read_config8(dev1, pos1 + LINK_FREQ(offs1));
215         old_freq &= 0x0f;
216         needs_reset |= old_freq != freq;
217         old_freq = pci_read_config8(dev2, pos2 + LINK_FREQ(offs2));
218         old_freq &= 0x0f;
219         needs_reset |= old_freq != freq;
220
221         /* Set the Calulcated link frequency */
222         pci_write_config8(dev1, pos1 + LINK_FREQ(offs1), freq);
223         pci_write_config8(dev2, pos2 + LINK_FREQ(offs2), freq);
224
225         /* Get the width capabilities */
226         width_cap1 = pci_read_config8(dev1, pos1 + LINK_WIDTH(offs1));
227         width_cap2 = pci_read_config8(dev2, pos2 + LINK_WIDTH(offs2));
228
229         /* Calculate dev1's input width */
230         ln_width1 = link_width_to_pow2[width_cap1 & 7];
231         ln_width2 = link_width_to_pow2[(width_cap2 >> 4) & 7];
232         if (ln_width1 > ln_width2) {
233                 ln_width1 = ln_width2;
234         }
235         width = pow2_to_link_width[ln_width1];
236         /* Calculate dev1's output width */
237         ln_width1 = link_width_to_pow2[(width_cap1 >> 4) & 7];
238         ln_width2 = link_width_to_pow2[width_cap2 & 7];
239         if (ln_width1 > ln_width2) {
240                 ln_width1 = ln_width2;
241         }
242         width |= pow2_to_link_width[ln_width1] << 4;
243
244         /* See if I am changing dev1's width */
245         old_width = pci_read_config8(dev1, pos1 + LINK_WIDTH(offs1) + 1);
246         old_width &= 0x77;
247         needs_reset |= old_width != width;
248
249         /* Set dev1's widths */
250         pci_write_config8(dev1, pos1 + LINK_WIDTH(offs1) + 1, width);
251
252         /* Calculate dev2's width */
253         width = ((width & 0x70) >> 4) | ((width & 0x7) << 4);
254
255         /* See if I am changing dev2's width */
256         old_width = pci_read_config8(dev2, pos2 + LINK_WIDTH(offs2) + 1);
257         old_width &= 0x77;
258         needs_reset |= old_width != width;
259
260         /* Set dev2's widths */
261         pci_write_config8(dev2, pos2 + LINK_WIDTH(offs2) + 1, width);
262
263         return needs_reset;
264 }
265 #if (USE_DCACHE_RAM == 1) && (K8_SCAN_PCI_BUS == 1)
266
267 #if RAMINIT_SYSINFO == 1
268 static void ht_setup_chainx(device_t udev, uint8_t upos, uint8_t bus, unsigned offset_unitid, struct sys_info *sysinfo);
269 static int scan_pci_bus( unsigned bus , struct sys_info *sysinfo) 
270 #else
271 static int ht_setup_chainx(device_t udev, uint8_t upos, uint8_t bus, unsigned offset_unitid);
272 static int scan_pci_bus( unsigned bus)
273 #endif
274 {
275         /*      
276                 here we already can access PCI_DEV(bus, 0, 0) to PCI_DEV(bus, 0x1f, 0x7)
277                 So We can scan these devices to find out if they are bridge 
278                 If it is pci bridge, We need to set busn in bridge, and go on
279                 For ht bridge, We need to set the busn in bridge and ht_setup_chainx, and the scan_pci_bus
280         */    
281         unsigned int devfn;
282         unsigned new_bus;
283         unsigned max_bus;
284
285         new_bus = (bus & 0xff); // mask out the reset_needed
286
287         if(new_bus<0x40) {
288                 max_bus = 0x3f;
289         } else if (new_bus<0x80) {
290                 max_bus = 0x7f;
291         } else if (new_bus<0xc0) {
292                 max_bus = 0xbf;
293         } else {
294                 max_bus = 0xff;
295         }
296
297         new_bus = bus;
298
299 #if 0
300 #if CONFIG_USE_PRINTK_IN_CAR
301         printk_debug("bus_num=%02x\r\n", bus);
302 #endif
303 #endif
304
305         for (devfn = 0; devfn <= 0xff; devfn++) { 
306                 uint8_t hdr_type;
307                 uint16_t class;
308                 uint32_t buses;
309                 device_t dev;
310                 uint16_t cr;
311                 dev = PCI_DEV((bus & 0xff), ((devfn>>3) & 0x1f), (devfn & 0x7));
312                 hdr_type = pci_read_config8(dev, PCI_HEADER_TYPE);
313                 class = pci_read_config16(dev, PCI_CLASS_DEVICE);
314
315 #if 0
316 #if CONFIG_USE_PRINTK_IN_CAR
317                 if(hdr_type !=0xff ) {
318                         printk_debug("dev=%02x fn=%02x hdr_type=%02x class=%04x\r\n", 
319                                 (devfn>>3)& 0x1f, (devfn & 0x7), hdr_type, class);
320                 }
321 #endif
322 #endif
323                 switch(hdr_type & 0x7f) {  /* header type */
324                         case PCI_HEADER_TYPE_BRIDGE:
325                                 if (class  != PCI_CLASS_BRIDGE_PCI) goto bad;
326                                 /* set the bus range dev */
327
328                                 /* Clear all status bits and turn off memory, I/O and master enables. */
329                                 cr = pci_read_config16(dev, PCI_COMMAND);
330                                 pci_write_config16(dev, PCI_COMMAND, 0x0000);
331                                 pci_write_config16(dev, PCI_STATUS, 0xffff);
332
333                                 buses = pci_read_config32(dev, PCI_PRIMARY_BUS);
334
335                                 buses &= 0xff000000;
336                                 new_bus++;
337                                 buses |= (((unsigned int) (bus & 0xff) << 0) |
338                                         ((unsigned int) (new_bus & 0xff) << 8) |
339                                         ((unsigned int) max_bus << 16));
340                                 pci_write_config32(dev, PCI_PRIMARY_BUS, buses);
341                                 
342                                 /* here we need to figure out if dev is a ht bridge
343                                         if it is ht bridge, we need to call ht_setup_chainx at first
344                                    Not verified --- yhlu
345                                 */
346                                 uint8_t upos;
347                                 upos = ht_lookup_host_capability(dev); // one func one ht sub
348                                 if (upos) { // sub ht chain
349                                         uint8_t busn;
350                                         busn = (new_bus & 0xff);
351                                         /* Make certain the HT bus is not enumerated */
352                                         ht_collapse_previous_enumeration(busn, 0);
353                                         /* scan the ht chain */
354                                         #if RAMINIT_SYSINFO == 1
355                                         ht_setup_chainx(dev,upos,busn, 0, sysinfo); // don't need offset unitid
356                                         #else
357                                         new_bus |= (ht_setup_chainx(dev, upos, busn, 0)<<16); // store reset_needed to upword
358                                         #endif
359                                 }
360                                 
361                                 #if RAMINIT_SYSINFO == 1                                
362                                 new_bus = scan_pci_bus(new_bus, sysinfo);
363                                 #else
364                                 new_bus = scan_pci_bus(new_bus);
365                                 #endif
366                                 /* set real max bus num in that */
367
368                                 buses = (buses & 0xff00ffff) |
369                                         ((unsigned int) (new_bus & 0xff) << 16);
370                                 pci_write_config32(dev, PCI_PRIMARY_BUS, buses);
371
372                                 pci_write_config16(dev, PCI_COMMAND, cr);
373
374                                 break;  
375                         default:
376                         bad:
377                                 ;
378                 }
379
380                 /* if this is not a multi function device, 
381                  * or the device is not present don't waste
382                  * time probing another function. 
383                  * Skip to next device. 
384                  */
385                 if ( ((devfn & 0x07) == 0x00) && ((hdr_type & 0x80) != 0x80))
386                 {
387                         devfn += 0x07;
388                 }
389         }
390         
391         return new_bus; 
392 }
393 #endif
394
395 #if RAMINIT_SYSINFO == 1
396 static void ht_setup_chainx(device_t udev, uint8_t upos, uint8_t bus, unsigned offset_unitid, struct sys_info *sysinfo)
397 #else
398 static int ht_setup_chainx(device_t udev, uint8_t upos, uint8_t bus, unsigned offset_unitid)
399 #endif
400 {
401         //even HT_CHAIN_UNITID_BASE == 0, we still can go through this function, because of end_of_chain check, also We need it to optimize link
402
403         uint8_t next_unitid, last_unitid;
404         unsigned uoffs;
405
406 #if RAMINIT_SYSINFO == 0
407         int reset_needed = 0;
408 #endif
409
410 #if HT_CHAIN_END_UNITID_BASE < HT_CHAIN_UNITID_BASE
411         //let't record the device of last ht device, So we can set the Unitid to HT_CHAIN_END_UNITID_BASE
412         unsigned real_last_unitid;
413         uint8_t real_last_pos;
414         int ht_dev_num = 0;
415 #endif
416
417         uoffs = PCI_HT_HOST_OFFS;
418         next_unitid = (offset_unitid) ? HT_CHAIN_UNITID_BASE:1;
419
420         do {
421                 uint32_t id;
422                 uint8_t pos;
423                 uint16_t flags, ctrl;
424                 uint8_t count;
425                 unsigned offs;
426         
427                 /* Wait until the link initialization is complete */
428                 do {
429                         ctrl = pci_read_config16(udev, upos + LINK_CTRL(uoffs));
430                         /* Is this the end of the hypertransport chain? */
431                         if (ctrl & (1 << 6)) {
432                                 goto end_of_chain;      
433                         }
434
435                         if (ctrl & ((1 << 4) | (1 << 8))) {
436                                /*
437                                 * Either the link has failed, or we have
438                                 * a CRC error.
439                                 * Sometimes this can happen due to link
440                                 * retrain, so lets knock it down and see
441                                 * if its transient
442                                 */
443                                 ctrl |= ((1 << 4) | (1 <<8)); // Link fail + Crc
444                                 pci_write_config16(udev, upos + LINK_CTRL(uoffs), ctrl);
445                                 ctrl = pci_read_config16(udev, upos + LINK_CTRL(uoffs));
446                                 if (ctrl & ((1 << 4) | (1 << 8))) {
447                                         print_err("Detected error on Hypertransport Link\n");
448                                         break;
449                                 }
450                         }
451                 } while((ctrl & (1 << 5)) == 0);
452         
453                 device_t dev = PCI_DEV(bus, 0, 0);
454                 last_unitid = next_unitid;
455
456                 id = pci_read_config32(dev, PCI_VENDOR_ID);
457
458                 /* If the chain is enumerated quit */
459                 if (    (id == 0xffffffff) || (id == 0x00000000) ||
460                         (id == 0x0000ffff) || (id == 0xffff0000))
461                 {
462                         break;
463                 }
464
465                 pos = ht_lookup_slave_capability(dev);
466                 if (!pos) {
467                         print_err("udev="); print_err_hex32(udev);
468                         print_err("\tupos="); print_err_hex32(upos);
469                         print_err("\tuoffs="); print_err_hex32(uoffs);
470                         print_err("\tHT link capability not found\r\n");
471                         break;
472                 }
473
474                 /* Update the Unitid of the current device */
475                 flags = pci_read_config16(dev, pos + PCI_CAP_FLAGS);
476                 flags &= ~0x1f; /* mask out the bse Unit ID */
477                 flags |= next_unitid & 0x1f;
478                 pci_write_config16(dev, pos + PCI_CAP_FLAGS, flags);
479
480                 /* Note the change in device number */
481                 dev = PCI_DEV(bus, next_unitid, 0);
482
483                 /* Compute the number of unitids consumed */
484                 count = (flags >> 5) & 0x1f;
485 #if HT_CHAIN_END_UNITID_BASE < HT_CHAIN_UNITID_BASE
486                 if(offset_unitid) {
487                         real_last_unitid = next_unitid;
488                         real_last_pos = pos;
489                         ht_dev_num++;
490                 }
491 #endif
492
493                 next_unitid += count;
494
495                 /* Find which side of the ht link we are on,
496                  * by reading which direction our last write to PCI_CAP_FLAGS
497                  * came from.
498                  */
499                 flags = pci_read_config16(dev, pos + PCI_CAP_FLAGS);
500                 offs = ((flags>>10) & 1) ? PCI_HT_SLAVE1_OFFS : PCI_HT_SLAVE0_OFFS;
501                
502                 #if RAMINIT_SYSINFO == 1
503                 /* store the link pair here and we will Setup the Hypertransport link later, after we get final FID/VID */
504                 {
505                         struct link_pair_st *link_pair = &sysinfo->link_pair[sysinfo->link_pair_num];
506                         link_pair->udev = udev;
507                         link_pair->upos = upos;
508                         link_pair->uoffs = uoffs;
509                         link_pair->dev = dev;
510                         link_pair->pos = pos;
511                         link_pair->offs = offs;
512                         sysinfo->link_pair_num++;
513                 }
514                 #else
515                 reset_needed |= ht_optimize_link(udev, upos, uoffs, dev, pos, offs);
516                 #endif
517
518                 /* Remeber the location of the last device */
519                 udev = dev;
520                 upos = pos;
521                 uoffs = ( offs != PCI_HT_SLAVE0_OFFS ) ? PCI_HT_SLAVE0_OFFS : PCI_HT_SLAVE1_OFFS;
522
523         } while((last_unitid != next_unitid) && (next_unitid <= 0x1f));
524
525 end_of_chain: ;
526         
527 #if HT_CHAIN_END_UNITID_BASE < HT_CHAIN_UNITID_BASE
528         if(offset_unitid && (ht_dev_num>0)  ) {
529                 uint16_t flags;
530                 int i;
531                 flags = pci_read_config16(PCI_DEV(bus,real_last_unitid,0), real_last_pos + PCI_CAP_FLAGS);
532                 flags &= ~0x1f;
533                 flags |= HT_CHAIN_END_UNITID_BASE & 0x1f;
534                 pci_write_config16(PCI_DEV(bus, real_last_unitid, 0), real_last_pos + PCI_CAP_FLAGS, flags);
535
536                 #if RAMINIT_SYSINFO == 1
537                 // Here need to change the dev in the array
538                 for(i=0;i<sysinfo->link_pair_num;i++)
539                 {
540                         struct link_pair_st *link_pair = &sysinfo->link_pair[i];
541                         if(link_pair->udev == PCI_DEV(bus, real_last_unitid, 0)) {
542                                 link_pair->udev = PCI_DEV(bus, HT_CHAIN_END_UNITID_BASE, 0);
543                                 continue;
544                         }
545                         if(link_pair->dev == PCI_DEV(bus, real_last_unitid, 0)) {
546                                 link_pair->dev = PCI_DEV(bus, HT_CHAIN_END_UNITID_BASE, 0);
547                         }
548                 }
549                 #endif
550
551         }
552 #endif
553
554 #if RAMINIT_SYSINFO == 0
555         return reset_needed;
556 #endif
557
558 }
559
560 #if RAMINIT_SYSINFO == 1
561 static void ht_setup_chain(device_t udev, unsigned upos, struct sys_info *sysinfo)
562 #else
563 static int ht_setup_chain(device_t udev, unsigned upos)
564 #endif
565 {
566         unsigned offset_unitid = 0;
567 #if HT_CHAIN_UNITID_BASE != 1
568         offset_unitid = 1;
569 #endif
570
571         /* Assumption the HT chain that is bus 0 has the HT I/O Hub on it.
572          * On most boards this just happens.  If a cpu has multiple
573          * non Coherent links the appropriate bus registers for the
574          * links needs to be programed to point at bus 0.
575          */
576
577         /* Make certain the HT bus is not enumerated */
578         ht_collapse_previous_enumeration(0, 0);
579
580 #if HT_CHAIN_UNITID_BASE != 1
581         offset_unitid = 1;
582 #endif
583
584 #if RAMINIT_SYSINFO == 1
585         ht_setup_chainx(udev, upos, 0, offset_unitid, sysinfo);
586 #else
587         return ht_setup_chainx(udev, upos, 0, offset_unitid);
588 #endif
589 }
590 static int optimize_link_read_pointer(uint8_t node, uint8_t linkn, uint8_t linkt, uint8_t val)
591 {
592         uint32_t dword, dword_old;
593         uint8_t link_type;
594         
595         /* This works on an Athlon64 because unimplemented links return 0 */
596         dword = pci_read_config32(PCI_DEV(0,0x18+node,0), 0x98 + (linkn * 0x20));
597         link_type = dword & 0xff;
598         
599         
600         if ( (link_type & 7) == linkt ) { /* Coherent Link only linkt = 3, ncoherent = 7*/
601                 dword_old = dword = pci_read_config32(PCI_DEV(0,0x18+node,3), 0xdc);
602                 dword &= ~( 0xff<<(linkn *8) );
603                 dword |= val << (linkn *8);
604         
605                 if (dword != dword_old) {
606                         pci_write_config32(PCI_DEV(0,0x18+node,3), 0xdc, dword);
607                         return 1;
608                 }
609         }
610         
611         return 0;
612 }
613
614 static int optimize_link_read_pointers_chain(uint8_t ht_c_num)
615 {
616         int reset_needed; 
617         uint8_t i;
618
619         reset_needed = 0;
620
621         for (i = 0; i < ht_c_num; i++) {
622                 uint32_t reg;
623                 uint8_t nodeid, linkn;
624                 uint8_t busn;
625                 uint8_t val;
626                 unsigned devn = 1;
627
628         #if HT_CHAIN_UNITID_BASE != 1
629                 #if SB_HT_CHAIN_UNITID_OFFSET_ONLY == 1
630                 if(i==0) // to check if it is sb ht chain
631                 #endif
632                         devn = HT_CHAIN_UNITID_BASE;
633         #endif
634
635                 reg = pci_read_config32(PCI_DEV(0,0x18,1), 0xe0 + i * 4);
636                 
637                 nodeid = ((reg & 0xf0)>>4); // nodeid
638                 linkn = ((reg & 0xf00)>>8); // link n
639                 busn = (reg & 0xff0000)>>16; //busn
640
641                 reg = pci_read_config32( PCI_DEV(busn, devn, 0), PCI_VENDOR_ID); // ? the chain dev maybe offseted
642                 if ( (reg & 0xffff) == PCI_VENDOR_ID_AMD) {
643                         val = 0x25;
644                 } else if ( (reg & 0xffff) == PCI_VENDOR_ID_NVIDIA ) {
645                         val = 0x25;//???
646                 } else {
647                         continue;
648                 }
649
650                 reset_needed |= optimize_link_read_pointer(nodeid, linkn, 0x07, val);
651
652         }
653
654         return reset_needed;
655 }
656
657 static int set_ht_link_buffer_count(uint8_t node, uint8_t linkn, uint8_t linkt, unsigned val)
658 {
659         uint32_t dword;
660         uint8_t link_type;
661         unsigned regpos;
662         device_t dev;
663
664         /* This works on an Athlon64 because unimplemented links return 0 */
665         regpos = 0x98 + (linkn * 0x20);
666         dev = PCI_DEV(0,0x18+node,0);
667         dword = pci_read_config32(dev, regpos);
668         link_type = dword & 0xff;
669
670         if ( (link_type & 0x7) == linkt ) { /* Coherent Link only linkt = 3, ncoherent = 7*/
671                 regpos = 0x90 + (linkn * 0x20);
672                 dword = pci_read_config32(dev, regpos );
673
674                 if (dword != val) {
675                         pci_write_config32(dev, regpos, val);
676                         return 1;
677                 }
678         }
679
680         return 0;
681 }
682 static int set_ht_link_buffer_counts_chain(uint8_t ht_c_num, unsigned vendorid,  unsigned val)
683 {
684         int reset_needed;
685         uint8_t i;
686
687         reset_needed = 0;
688
689         for (i = 0; i < ht_c_num; i++) {
690                 uint32_t reg;
691                 uint8_t nodeid, linkn;
692                 uint8_t busn;
693                 unsigned devn = 1;
694
695         #if HT_CHAIN_UNITID_BASE != 1
696                 #if SB_HT_CHAIN_UNITID_OFFSET_ONLY == 1
697                 if(i==0) // to check if it is sb ht chain
698                 #endif
699                         devn = HT_CHAIN_UNITID_BASE;
700         #endif
701
702                 reg = pci_read_config32(PCI_DEV(0,0x18,1), 0xe0 + i * 4);
703                 if((reg & 3) != 3) continue; // not enabled
704
705                 nodeid = ((reg & 0xf0)>>4); // nodeid
706                 linkn = ((reg & 0xf00)>>8); // link n
707                 busn = (reg & 0xff0000)>>16; //busn
708
709                 reg = pci_read_config32( PCI_DEV(busn, devn, 0), PCI_VENDOR_ID); //1?
710                 if ( (reg & 0xffff) == vendorid ) {
711                         reset_needed |= set_ht_link_buffer_count(nodeid, linkn, 0x07,val);
712                 }
713         }
714
715         return reset_needed;
716 }
717
718
719 #if RAMINIT_SYSINFO == 1
720 static void ht_setup_chains(uint8_t ht_c_num, struct sys_info *sysinfo)
721 #else
722 static int ht_setup_chains(uint8_t ht_c_num)
723 #endif
724 {
725         /* Assumption the HT chain that is bus 0 has the HT I/O Hub on it. 
726          * On most boards this just happens.  If a cpu has multiple
727          * non Coherent links the appropriate bus registers for the
728          * links needs to be programed to point at bus 0.
729          */
730         uint8_t upos;
731         device_t udev;
732         uint8_t i;
733
734 #if RAMINIT_SYSINFO == 0
735         int reset_needed = 0;
736 #else
737         sysinfo->link_pair_num = 0;
738 #endif
739
740         // first one is SB Chain
741         for (i = 0; i < ht_c_num; i++) {
742                 uint32_t reg;
743                 uint8_t devpos;
744                 unsigned regpos;
745                 uint32_t dword;
746                 uint8_t busn;
747                 #if (USE_DCACHE_RAM == 1) && (K8_SCAN_PCI_BUS == 1)
748                 unsigned bus;
749                 #endif
750                 unsigned offset_unitid = 0;
751                 
752                 reg = pci_read_config32(PCI_DEV(0,0x18,1), 0xe0 + i * 4);
753
754                 //We need setup 0x94, 0xb4, and 0xd4 according to the reg
755                 devpos = ((reg & 0xf0)>>4)+0x18; // nodeid; it will decide 0x18 or 0x19
756                 regpos = ((reg & 0xf00)>>8) * 0x20 + 0x94; // link n; it will decide 0x94 or 0xb4, 0x0xd4;
757                 busn = (reg & 0xff0000)>>16;
758                 
759                 dword = pci_read_config32( PCI_DEV(0, devpos, 0), regpos) ;
760                 dword &= ~(0xffff<<8);
761                 dword |= (reg & 0xffff0000)>>8;
762                 pci_write_config32( PCI_DEV(0, devpos,0), regpos , dword);
763         
764
765         #if HT_CHAIN_UNITID_BASE != 1
766                 #if SB_HT_CHAIN_UNITID_OFFSET_ONLY == 1
767                 if(i==0) // to check if it is sb ht chain
768                 #endif
769                         offset_unitid = 1;
770         #endif
771         
772                 /* Make certain the HT bus is not enumerated */
773                 ht_collapse_previous_enumeration(busn, offset_unitid);
774
775                 upos = ((reg & 0xf00)>>8) * 0x20 + 0x80;
776                 udev =  PCI_DEV(0, devpos, 0);
777
778 #if RAMINIT_SYSINFO == 1
779                 ht_setup_chainx(udev,upos,busn, offset_unitid, sysinfo); // all not
780 #else
781                 reset_needed |= ht_setup_chainx(udev,upos,busn, offset_unitid); //all not
782 #endif
783
784                 #if (USE_DCACHE_RAM == 1) && (K8_SCAN_PCI_BUS == 1)
785                 /* You can use use this in romcc, because there is function call in romcc, recursive will kill you */
786                 bus = busn; // we need 32 bit 
787 #if RAMINIT_SYSINFO == 1
788                 scan_pci_bus(bus, sysinfo);
789 #else
790                 reset_needed |= (scan_pci_bus(bus)>>16); // take out reset_needed that stored in upword
791 #endif
792                 #endif
793         }
794
795 #if RAMINIT_SYSINFO == 0
796         reset_needed |= optimize_link_read_pointers_chain(ht_c_num);
797
798         return reset_needed;
799 #endif
800
801 }
802
803 #if defined (__GNUC__)
804 static inline unsigned get_nodes(void);
805 #endif
806
807 #if RAMINIT_SYSINFO == 1
808 static void ht_setup_chains_x(struct sys_info *sysinfo)
809 #else
810 static int ht_setup_chains_x(void)
811 #endif
812 {               
813         uint8_t nodeid;
814         uint32_t reg; 
815         uint32_t tempreg;
816         uint8_t next_busn;
817         uint8_t ht_c_num;
818         uint8_t nodes;
819 #if K8_ALLOCATE_IO_RANGE == 1   
820         unsigned next_io_base;
821 #endif
822
823         nodes = get_nodes();     
824  
825         /* read PCI_DEV(0,0x18,0) 0x64 bit [8:9] to find out SbLink m */
826         reg = pci_read_config32(PCI_DEV(0, 0x18, 0), 0x64);
827         /* update PCI_DEV(0, 0x18, 1) 0xe0 to 0x05000m03, and next_busn=0x3f+1 */
828         print_linkn_in("SBLink=", ((reg>>8) & 3) );
829 #if RAMINIT_SYSINFO == 1
830         sysinfo->sblk = (reg>>8) & 3;
831         sysinfo->sbbusn = 0;
832         sysinfo->nodes = nodes;
833 #endif
834         tempreg = 3 | ( 0<<4) | (((reg>>8) & 3)<<8) | (0<<16)| (0x3f<<24);
835         pci_write_config32(PCI_DEV(0, 0x18, 1), 0xe0, tempreg);
836
837         next_busn=0x3f+1; /* 0 will be used ht chain with SB we need to keep SB in bus0 in auto stage*/
838
839 #if K8_ALLOCATE_IO_RANGE == 1
840         /* io range allocation */
841         tempreg = 0 | (((reg>>8) & 0x3) << 4 )|  (0x3<<12); //limit
842         pci_write_config32(PCI_DEV(0, 0x18, 1), 0xC4, tempreg);
843         tempreg = 3 | ( 3<<4) | (0<<12);        //base
844         pci_write_config32(PCI_DEV(0, 0x18, 1), 0xC0, tempreg);
845         next_io_base = 0x3+0x1;
846 #endif
847
848         /* clean others */
849         for(ht_c_num=1;ht_c_num<4; ht_c_num++) {
850                 pci_write_config32(PCI_DEV(0, 0x18, 1), 0xe0 + ht_c_num * 4, 0);
851
852 #if K8_ALLOCATE_IO_RANGE == 1
853                 /* io range allocation */
854                 pci_write_config32(PCI_DEV(0, 0x18, 1), 0xc4 + ht_c_num * 8, 0);
855                 pci_write_config32(PCI_DEV(0, 0x18, 1), 0xc0 + ht_c_num * 8, 0);
856 #endif
857         }
858  
859         for(nodeid=0; nodeid<nodes; nodeid++) {
860                 device_t dev; 
861                 uint8_t linkn;
862                 dev = PCI_DEV(0, 0x18+nodeid,0);
863                 for(linkn = 0; linkn<3; linkn++) {
864                         unsigned regpos;
865                         regpos = 0x98 + 0x20 * linkn;
866                         reg = pci_read_config32(dev, regpos);
867                         if ((reg & 0x17) != 7) continue; /* it is not non conherent or not connected*/
868                         print_linkn_in("NC node|link=", ((nodeid & 0xf)<<4)|(linkn & 0xf));
869                         tempreg = 3 | (nodeid <<4) | (linkn<<8);
870                         /*compare (temp & 0xffff), with (PCI(0, 0x18, 1) 0xe0 to 0xec & 0xfffff) */
871                         for(ht_c_num=0;ht_c_num<4; ht_c_num++) {
872                                 reg = pci_read_config32(PCI_DEV(0, 0x18, 1), 0xe0 + ht_c_num * 4);
873                                 if(((reg & 0xffff) == (tempreg & 0xffff)) || ((reg & 0xffff) == 0x0000)) {  /*we got it*/
874                                         break;
875                                 }
876                         }
877                         if(ht_c_num == 4) break; /*used up only 4 non conherent allowed*/
878                         /*update to 0xe0...*/
879                         if((reg & 0xf) == 3) continue; /*SbLink so don't touch it */
880                         print_linkn_in("\tbusn=", next_busn);
881                         tempreg |= (next_busn<<16)|((next_busn+0x3f)<<24);
882                         pci_write_config32(PCI_DEV(0, 0x18, 1), 0xe0 + ht_c_num * 4, tempreg);
883                         next_busn+=0x3f+1;
884
885 #if K8_ALLOCATE_IO_RANGE == 1                   
886                         /* io range allocation */
887                         tempreg = nodeid | (linkn<<4) |  ((next_io_base+0x3)<<12); //limit
888                         pci_write_config32(PCI_DEV(0, 0x18, 1), 0xC4 + ht_c_num * 8, tempreg);
889                         tempreg = 3 /*| ( 3<<4)*/ | (next_io_base<<12);        //base :ISA and VGA ?
890                         pci_write_config32(PCI_DEV(0, 0x18, 1), 0xC0 + ht_c_num * 8, tempreg);
891                         next_io_base += 0x3+0x1;
892 #endif
893
894                 }
895         }
896         /*update 0xe0, 0xe4, 0xe8, 0xec from PCI_DEV(0, 0x18,1) to PCI_DEV(0, 0x19,1) to PCI_DEV(0, 0x1f,1);*/
897
898         for(nodeid = 1; nodeid<nodes; nodeid++) {
899                 int i;
900                 device_t dev;
901                 dev = PCI_DEV(0, 0x18+nodeid,1);
902                 for(i = 0; i< 4; i++) {
903                         unsigned regpos;
904                         regpos = 0xe0 + i * 4;
905                         reg = pci_read_config32(PCI_DEV(0, 0x18, 1), regpos);
906                         pci_write_config32(dev, regpos, reg);
907                 }
908
909 #if K8_ALLOCATE_IO_RANGE == 1
910                 /* io range allocation */
911                 for(i = 0; i< 4; i++) {
912                         unsigned regpos;
913                         regpos = 0xc4 + i * 8;
914                         reg = pci_read_config32(PCI_DEV(0, 0x18, 1), regpos);
915                         pci_write_config32(dev, regpos, reg);
916                 }
917                 for(i = 0; i< 4; i++) {
918                         unsigned regpos;
919                         regpos = 0xc0 + i * 8;
920                         reg = pci_read_config32(PCI_DEV(0, 0x18, 1), regpos);
921                         pci_write_config32(dev, regpos, reg);
922                 }
923 #endif
924         }
925         
926         /* recount ht_c_num*/
927         uint8_t i=0;
928         for(ht_c_num=0;ht_c_num<4; ht_c_num++) {
929                 reg = pci_read_config32(PCI_DEV(0, 0x18, 1), 0xe0 + ht_c_num * 4);
930                 if(((reg & 0xf) != 0x0)) {
931                         i++;
932                 }
933         }
934
935 #if RAMINIT_SYSINFO == 1
936         sysinfo->ht_c_num = i;
937         ht_setup_chains(i, sysinfo);
938         sysinfo->sbdn = get_sbdn(sysinfo->sbbusn);
939 #else
940         return ht_setup_chains(i);
941 #endif
942
943 }
944
945 #if RAMINIT_SYSINFO == 1
946 static int optimize_link_incoherent_ht(struct sys_info *sysinfo)
947 {
948         // We need to use recorded link pair info to optimize the link
949         int i;
950         int reset_needed = 0;
951         
952         unsigned link_pair_num = sysinfo->link_pair_num;
953
954         for(i=0; i< link_pair_num; i++) {       
955                 struct link_pair_st *link_pair= &sysinfo->link_pair[i];
956                 reset_needed |= ht_optimize_link(link_pair->udev, link_pair->upos, link_pair->uoffs, link_pair->dev, link_pair->pos, link_pair->offs);
957         }
958
959         reset_needed |= optimize_link_read_pointers_chain(sysinfo->ht_c_num);
960
961         return reset_needed;
962
963 }
964 #endif
965
966
967