8a2a2c56f117f0efae9b59a3f817630c6ac80703
[dragonfly.git] / sys / platform / pc64 / x86_64 / mp_machdep.c
1 /*
2  * Copyright (c) 1996, by Steve Passe
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. The name of the developer may NOT be used to endorse or promote products
11  *    derived from this software without specific prior written permission.
12  *
13  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
14  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
16  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
17  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
18  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
19  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
20  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
21  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
22  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
23  * SUCH DAMAGE.
24  *
25  * $FreeBSD: src/sys/i386/i386/mp_machdep.c,v 1.115.2.15 2003/03/14 21:22:35 jhb Exp $
26  */
27
28 #include "opt_cpu.h"
29
30 #include <sys/param.h>
31 #include <sys/systm.h>
32 #include <sys/kernel.h>
33 #include <sys/sysctl.h>
34 #include <sys/malloc.h>
35 #include <sys/memrange.h>
36 #include <sys/cons.h>   /* cngetc() */
37 #include <sys/machintr.h>
38
39 #include <sys/mplock2.h>
40
41 #include <vm/vm.h>
42 #include <vm/vm_param.h>
43 #include <vm/pmap.h>
44 #include <vm/vm_kern.h>
45 #include <vm/vm_extern.h>
46 #include <sys/lock.h>
47 #include <vm/vm_map.h>
48 #include <sys/user.h>
49 #ifdef GPROF 
50 #include <sys/gmon.h>
51 #endif
52
53 #include <machine/smp.h>
54 #include <machine_base/apic/apicreg.h>
55 #include <machine/atomic.h>
56 #include <machine/cpufunc.h>
57 #include <machine_base/apic/lapic.h>
58 #include <machine/psl.h>
59 #include <machine/segments.h>
60 #include <machine/tss.h>
61 #include <machine/specialreg.h>
62 #include <machine/globaldata.h>
63 #include <machine/pmap_inval.h>
64
65 #include <machine/md_var.h>             /* setidt() */
66 #include <machine_base/icu/icu.h>       /* IPIs */
67 #include <machine_base/apic/ioapic_abi.h>
68 #include <machine/intr_machdep.h>       /* IPIs */
69
70 #define WARMBOOT_TARGET         0
71 #define WARMBOOT_OFF            (KERNBASE + 0x0467)
72 #define WARMBOOT_SEG            (KERNBASE + 0x0469)
73
74 #define BIOS_BASE               (0xf0000)
75 #define BIOS_BASE2              (0xe0000)
76 #define BIOS_SIZE               (0x10000)
77 #define BIOS_COUNT              (BIOS_SIZE/4)
78
79 #define CMOS_REG                (0x70)
80 #define CMOS_DATA               (0x71)
81 #define BIOS_RESET              (0x0f)
82 #define BIOS_WARM               (0x0a)
83
84 #define PROCENTRY_FLAG_EN       0x01
85 #define PROCENTRY_FLAG_BP       0x02
86 #define IOAPICENTRY_FLAG_EN     0x01
87
88
89 /* MP Floating Pointer Structure */
90 typedef struct MPFPS {
91         char    signature[4];
92         u_int32_t pap;
93         u_char  length;
94         u_char  spec_rev;
95         u_char  checksum;
96         u_char  mpfb1;
97         u_char  mpfb2;
98         u_char  mpfb3;
99         u_char  mpfb4;
100         u_char  mpfb5;
101 }      *mpfps_t;
102
103 /* MP Configuration Table Header */
104 typedef struct MPCTH {
105         char    signature[4];
106         u_short base_table_length;
107         u_char  spec_rev;
108         u_char  checksum;
109         u_char  oem_id[8];
110         u_char  product_id[12];
111         u_int32_t oem_table_pointer;
112         u_short oem_table_size;
113         u_short entry_count;
114         u_int32_t apic_address;
115         u_short extended_table_length;
116         u_char  extended_table_checksum;
117         u_char  reserved;
118 }      *mpcth_t;
119
120
121 typedef struct PROCENTRY {
122         u_char  type;
123         u_char  apic_id;
124         u_char  apic_version;
125         u_char  cpu_flags;
126         u_int32_t cpu_signature;
127         u_int32_t feature_flags;
128         u_int32_t reserved1;
129         u_int32_t reserved2;
130 }      *proc_entry_ptr;
131
132 typedef struct BUSENTRY {
133         u_char  type;
134         u_char  bus_id;
135         char    bus_type[6];
136 }      *bus_entry_ptr;
137
138 typedef struct IOAPICENTRY {
139         u_char  type;
140         u_char  apic_id;
141         u_char  apic_version;
142         u_char  apic_flags;
143         u_int32_t apic_address;
144 }      *io_apic_entry_ptr;
145
146 typedef struct INTENTRY {
147         u_char  type;
148         u_char  int_type;
149         u_short int_flags;
150         u_char  src_bus_id;
151         u_char  src_bus_irq;
152         u_char  dst_apic_id;
153         u_char  dst_apic_int;
154 }      *int_entry_ptr;
155
156 /* descriptions of MP basetable entries */
157 typedef struct BASETABLE_ENTRY {
158         u_char  type;
159         u_char  length;
160         char    name[16];
161 }       basetable_entry;
162
163 struct mptable_pos {
164         mpfps_t         mp_fps;
165         mpcth_t         mp_cth;
166         vm_size_t       mp_cth_mapsz;   
167 };
168
169 #define MPTABLE_POS_USE_DEFAULT(mpt) \
170         ((mpt)->mp_fps->mpfb1 != 0 || (mpt)->mp_cth == NULL)
171
172 struct mptable_bus {
173         int             mb_id;
174         int             mb_type;        /* MPTABLE_BUS_ */
175         TAILQ_ENTRY(mptable_bus) mb_link;
176 };
177
178 #define MPTABLE_BUS_ISA         0
179 #define MPTABLE_BUS_PCI         1
180
181 struct mptable_bus_info {
182         TAILQ_HEAD(, mptable_bus) mbi_list;
183 };
184
185 struct mptable_pci_int {
186         int             mpci_bus;
187         int             mpci_dev;
188         int             mpci_pin;
189
190         int             mpci_ioapic_idx;
191         int             mpci_ioapic_pin;
192         TAILQ_ENTRY(mptable_pci_int) mpci_link;
193 };
194
195 struct mptable_ioapic {
196         int             mio_idx;
197         int             mio_apic_id;
198         uint32_t        mio_addr;
199         int             mio_gsi_base;
200         int             mio_npin;
201         TAILQ_ENTRY(mptable_ioapic) mio_link;
202 };
203
204 typedef int     (*mptable_iter_func)(void *, const void *, int);
205
206 /*
207  * this code MUST be enabled here and in mpboot.s.
208  * it follows the very early stages of AP boot by placing values in CMOS ram.
209  * it NORMALLY will never be needed and thus the primitive method for enabling.
210  *
211  */
212 #if defined(CHECK_POINTS)
213 #define CHECK_READ(A)    (outb(CMOS_REG, (A)), inb(CMOS_DATA))
214 #define CHECK_WRITE(A,D) (outb(CMOS_REG, (A)), outb(CMOS_DATA, (D)))
215
216 #define CHECK_INIT(D);                          \
217         CHECK_WRITE(0x34, (D));                 \
218         CHECK_WRITE(0x35, (D));                 \
219         CHECK_WRITE(0x36, (D));                 \
220         CHECK_WRITE(0x37, (D));                 \
221         CHECK_WRITE(0x38, (D));                 \
222         CHECK_WRITE(0x39, (D));
223
224 #define CHECK_PRINT(S);                         \
225         kprintf("%s: %d, %d, %d, %d, %d, %d\n", \
226            (S),                                 \
227            CHECK_READ(0x34),                    \
228            CHECK_READ(0x35),                    \
229            CHECK_READ(0x36),                    \
230            CHECK_READ(0x37),                    \
231            CHECK_READ(0x38),                    \
232            CHECK_READ(0x39));
233
234 #else                           /* CHECK_POINTS */
235
236 #define CHECK_INIT(D)
237 #define CHECK_PRINT(S)
238
239 #endif                          /* CHECK_POINTS */
240
241 /*
242  * Values to send to the POST hardware.
243  */
244 #define MP_BOOTADDRESS_POST     0x10
245 #define MP_PROBE_POST           0x11
246 #define MPTABLE_PASS1_POST      0x12
247
248 #define MP_START_POST           0x13
249 #define MP_ENABLE_POST          0x14
250 #define MPTABLE_PASS2_POST      0x15
251
252 #define START_ALL_APS_POST      0x16
253 #define INSTALL_AP_TRAMP_POST   0x17
254 #define START_AP_POST           0x18
255
256 #define MP_ANNOUNCE_POST        0x19
257
258 /** XXX FIXME: where does this really belong, isa.h/isa.c perhaps? */
259 int     current_postcode;
260
261 /** XXX FIXME: what system files declare these??? */
262 extern struct region_descriptor r_gdt, r_idt;
263
264 int     mp_naps;                /* # of Applications processors */
265 extern  int nkpt;
266
267 u_int32_t cpu_apic_versions[NAPICID];   /* populated during mptable scan */
268 int64_t tsc0_offset;
269 extern int64_t tsc_offsets[];
270
271 extern u_long ebda_addr;
272
273 #ifdef SMP /* APIC-IO */
274 struct apic_intmapinfo  int_to_apicintpin[APIC_INTMAPSIZE];
275 #endif
276
277 /*
278  * APIC ID logical/physical mapping structures.
279  * We oversize these to simplify boot-time config.
280  */
281 int     cpu_num_to_apic_id[NAPICID];
282 int     apic_id_to_logical[NAPICID];
283
284 /* AP uses this during bootstrap.  Do not staticize.  */
285 char *bootSTK;
286 static int bootAP;
287
288 struct pcb stoppcbs[MAXCPU];
289
290 extern inthand_t IDTVEC(fast_syscall), IDTVEC(fast_syscall32);
291
292 static basetable_entry basetable_entry_types[] =
293 {
294         {0, 20, "Processor"},
295         {1, 8, "Bus"},
296         {2, 8, "I/O APIC"},
297         {3, 8, "I/O INT"},
298         {4, 8, "Local INT"}
299 };
300
301 /*
302  * Local data and functions.
303  */
304
305 static u_int    boot_address;
306 static u_int    base_memory;
307 static int      mp_finish;
308 static int      mp_finish_lapic;
309
310 static void     mp_enable(u_int boot_addr);
311
312 static int      mptable_iterate_entries(const mpcth_t,
313                     mptable_iter_func, void *);
314 static int      mptable_search(void);
315 static long     mptable_search_sig(u_int32_t target, int count);
316 static int      mptable_hyperthread_fixup(cpumask_t, int);
317 static int      mptable_map(struct mptable_pos *);
318 static void     mptable_unmap(struct mptable_pos *);
319 static void     mptable_bus_info_alloc(const mpcth_t,
320                     struct mptable_bus_info *);
321 static void     mptable_bus_info_free(struct mptable_bus_info *);
322
323 static int      mptable_lapic_probe(struct lapic_enumerator *);
324 static void     mptable_lapic_enumerate(struct lapic_enumerator *);
325 static void     mptable_lapic_default(void);
326
327 static int      mptable_ioapic_probe(struct ioapic_enumerator *);
328 static void     mptable_ioapic_enumerate(struct ioapic_enumerator *);
329
330 static int      start_all_aps(u_int boot_addr);
331 #if 0
332 static void     install_ap_tramp(u_int boot_addr);
333 #endif
334 static int      start_ap(struct mdglobaldata *gd, u_int boot_addr, int smibest);
335 static int      smitest(void);
336
337 static cpumask_t smp_startup_mask = 1;  /* which cpus have been started */
338 static cpumask_t smp_lapic_mask = 1;    /* which cpus have lapic been inited */
339 cpumask_t smp_active_mask = 1;  /* which cpus are ready for IPIs etc? */
340 SYSCTL_INT(_machdep, OID_AUTO, smp_active, CTLFLAG_RD, &smp_active_mask, 0, "");
341 static u_int    bootMP_size;
342
343 int                     imcr_present;
344
345 static vm_paddr_t       mptable_fps_phyaddr;
346 static int              mptable_use_default;
347 static TAILQ_HEAD(mptable_pci_int_list, mptable_pci_int) mptable_pci_int_list =
348         TAILQ_HEAD_INITIALIZER(mptable_pci_int_list);
349 static TAILQ_HEAD(mptable_ioapic_list, mptable_ioapic) mptable_ioapic_list =
350         TAILQ_HEAD_INITIALIZER(mptable_ioapic_list);
351
352 /*
353  * Calculate usable address in base memory for AP trampoline code.
354  */
355 u_int
356 mp_bootaddress(u_int basemem)
357 {
358         POSTCODE(MP_BOOTADDRESS_POST);
359
360         base_memory = basemem;
361
362         bootMP_size = mptramp_end - mptramp_start;
363         boot_address = trunc_page(basemem * 1024); /* round down to 4k boundary */
364         if (((basemem * 1024) - boot_address) < bootMP_size)
365                 boot_address -= PAGE_SIZE;      /* not enough, lower by 4k */
366         /* 3 levels of page table pages */
367         mptramp_pagetables = boot_address - (PAGE_SIZE * 3);
368
369         return mptramp_pagetables;
370 }
371
372
373 static void
374 mptable_probe(void)
375 {
376         struct mptable_pos mpt;
377         int error;
378
379         KKASSERT(mptable_fps_phyaddr == 0);
380
381         mptable_fps_phyaddr = mptable_search();
382         if (mptable_fps_phyaddr == 0)
383                 return;
384
385         error = mptable_map(&mpt);
386         if (error) {
387                 mptable_fps_phyaddr = 0;
388                 return;
389         }
390
391         if (MPTABLE_POS_USE_DEFAULT(&mpt)) {
392                 kprintf("MPTABLE: use default configuration\n");
393                 mptable_use_default = 1;
394         }
395         if (mpt.mp_fps->mpfb2 & 0x80)
396                 imcr_present = 1;
397
398         mptable_unmap(&mpt);
399 }
400 SYSINIT(mptable_probe, SI_BOOT2_PRESMP, SI_ORDER_FIRST, mptable_probe, 0);
401
402 /*
403  * Look for an Intel MP spec table (ie, SMP capable hardware).
404  */
405 static int
406 mptable_search(void)
407 {
408         long    x;
409         u_int32_t target;
410  
411         POSTCODE(MP_PROBE_POST);
412
413         /* see if EBDA exists */
414         if (ebda_addr != 0) {
415                 /* search first 1K of EBDA */
416                 target = (u_int32_t)ebda_addr;
417                 if ((x = mptable_search_sig(target, 1024 / 4)) > 0)
418                         return x;
419         } else {
420                 /* last 1K of base memory, effective 'top of base' passed in */
421                 target = (u_int32_t)(base_memory - 0x400);
422                 if ((x = mptable_search_sig(target, 1024 / 4)) > 0)
423                         return x;
424         }
425
426         /* search the BIOS */
427         target = (u_int32_t)BIOS_BASE;
428         if ((x = mptable_search_sig(target, BIOS_COUNT)) > 0)
429                 return x;
430
431         /* search the extended BIOS */
432         target = (u_int32_t)BIOS_BASE2;
433         if ((x = mptable_search_sig(target, BIOS_COUNT)) > 0)
434                 return x;
435
436         /* nothing found */
437         return 0;
438 }
439
440 static int
441 mptable_iterate_entries(const mpcth_t cth, mptable_iter_func func, void *arg)
442 {
443         int count, total_size;
444         const void *position;
445
446         KKASSERT(cth->base_table_length >= sizeof(struct MPCTH));
447         total_size = cth->base_table_length - sizeof(struct MPCTH);
448         position = (const uint8_t *)cth + sizeof(struct MPCTH);
449         count = cth->entry_count;
450
451         while (count--) {
452                 int type, error;
453
454                 KKASSERT(total_size >= 0);
455                 if (total_size == 0) {
456                         kprintf("invalid base MP table, "
457                                 "entry count and length mismatch\n");
458                         return EINVAL;
459                 }
460
461                 type = *(const uint8_t *)position;
462                 switch (type) {
463                 case 0: /* processor_entry */
464                 case 1: /* bus_entry */
465                 case 2: /* io_apic_entry */
466                 case 3: /* int_entry */
467                 case 4: /* int_entry */
468                         break;
469                 default:
470                         kprintf("unknown base MP table entry type %d\n", type);
471                         return EINVAL;
472                 }
473
474                 if (total_size < basetable_entry_types[type].length) {
475                         kprintf("invalid base MP table length, "
476                                 "does not contain all entries\n");
477                         return EINVAL;
478                 }
479                 total_size -= basetable_entry_types[type].length;
480
481                 error = func(arg, position, type);
482                 if (error)
483                         return error;
484
485                 position = (const uint8_t *)position +
486                     basetable_entry_types[type].length;
487         }
488         return 0;
489 }
490
491
492 /*
493  * Startup the SMP processors.
494  */
495 void
496 mp_start(void)
497 {
498         POSTCODE(MP_START_POST);
499         mp_enable(boot_address);
500 }
501
502
503 /*
504  * Print various information about the SMP system hardware and setup.
505  */
506 void
507 mp_announce(void)
508 {
509         int     x;
510
511         POSTCODE(MP_ANNOUNCE_POST);
512
513         kprintf("DragonFly/MP: Multiprocessor motherboard\n");
514         kprintf(" cpu0 (BSP): apic id: %2d", CPU_TO_ID(0));
515         kprintf(", version: 0x%08x\n", cpu_apic_versions[0]);
516         for (x = 1; x <= mp_naps; ++x) {
517                 kprintf(" cpu%d (AP):  apic id: %2d", x, CPU_TO_ID(x));
518                 kprintf(", version: 0x%08x\n", cpu_apic_versions[x]);
519         }
520
521         if (!apic_io_enable)
522                 kprintf(" Warning: APIC I/O disabled\n");
523 }
524
525 /*
526  * AP cpu's call this to sync up protected mode.
527  *
528  * WARNING! %gs is not set up on entry.  This routine sets up %gs.
529  */
530 void
531 init_secondary(void)
532 {
533         int     gsel_tss;
534         int     x, myid = bootAP;
535         u_int64_t msr, cr0;
536         struct mdglobaldata *md;
537         struct privatespace *ps;
538
539         ps = &CPU_prvspace[myid];
540
541         gdt_segs[GPROC0_SEL].ssd_base =
542                 (long) &ps->mdglobaldata.gd_common_tss;
543         ps->mdglobaldata.mi.gd_prvspace = ps;
544
545         /* We fill the 32-bit segment descriptors */
546         for (x = 0; x < NGDT; x++) {
547                 if (x != GPROC0_SEL && x != (GPROC0_SEL + 1))
548                         ssdtosd(&gdt_segs[x], &gdt[myid * NGDT + x]);
549         }
550         /* And now a 64-bit one */
551         ssdtosyssd(&gdt_segs[GPROC0_SEL],
552             (struct system_segment_descriptor *)&gdt[myid * NGDT + GPROC0_SEL]);
553
554         r_gdt.rd_limit = NGDT * sizeof(gdt[0]) - 1;
555         r_gdt.rd_base = (long) &gdt[myid * NGDT];
556         lgdt(&r_gdt);                   /* does magic intra-segment return */
557
558         /* lgdt() destroys the GSBASE value, so we load GSBASE after lgdt() */
559         wrmsr(MSR_FSBASE, 0);           /* User value */
560         wrmsr(MSR_GSBASE, (u_int64_t)ps);
561         wrmsr(MSR_KGSBASE, 0);          /* XXX User value while we're in the kernel */
562
563         lidt(&r_idt);
564
565 #if 0
566         lldt(_default_ldt);
567         mdcpu->gd_currentldt = _default_ldt;
568 #endif
569
570         gsel_tss = GSEL(GPROC0_SEL, SEL_KPL);
571         gdt[myid * NGDT + GPROC0_SEL].sd_type = SDT_SYSTSS;
572
573         md = mdcpu;     /* loaded through %gs:0 (mdglobaldata.mi.gd_prvspace)*/
574
575         md->gd_common_tss.tss_rsp0 = 0; /* not used until after switch */
576 #if 0 /* JG XXX */
577         md->gd_common_tss.tss_ioopt = (sizeof md->gd_common_tss) << 16;
578 #endif
579         md->gd_tss_gdt = &gdt[myid * NGDT + GPROC0_SEL];
580         md->gd_common_tssd = *md->gd_tss_gdt;
581
582         /* double fault stack */
583         md->gd_common_tss.tss_ist1 =
584                 (long)&md->mi.gd_prvspace->idlestack[
585                         sizeof(md->mi.gd_prvspace->idlestack)];
586
587         ltr(gsel_tss);
588
589         /*
590          * Set to a known state:
591          * Set by mpboot.s: CR0_PG, CR0_PE
592          * Set by cpu_setregs: CR0_NE, CR0_MP, CR0_TS, CR0_WP, CR0_AM
593          */
594         cr0 = rcr0();
595         cr0 &= ~(CR0_CD | CR0_NW | CR0_EM);
596         load_cr0(cr0);
597
598         /* Set up the fast syscall stuff */
599         msr = rdmsr(MSR_EFER) | EFER_SCE;
600         wrmsr(MSR_EFER, msr);
601         wrmsr(MSR_LSTAR, (u_int64_t)IDTVEC(fast_syscall));
602         wrmsr(MSR_CSTAR, (u_int64_t)IDTVEC(fast_syscall32));
603         msr = ((u_int64_t)GSEL(GCODE_SEL, SEL_KPL) << 32) |
604               ((u_int64_t)GSEL(GUCODE32_SEL, SEL_UPL) << 48);
605         wrmsr(MSR_STAR, msr);
606         wrmsr(MSR_SF_MASK, PSL_NT|PSL_T|PSL_I|PSL_C|PSL_D);
607
608         pmap_set_opt();         /* PSE/4MB pages, etc */
609 #if JGXXX
610         /* Initialize the PAT MSR. */
611         pmap_init_pat();
612 #endif
613
614         /* set up CPU registers and state */
615         cpu_setregs();
616
617         /* set up SSE/NX registers */
618         initializecpu();
619
620         /* set up FPU state on the AP */
621         npxinit(__INITIAL_NPXCW__);
622
623         /* disable the APIC, just to be SURE */
624         lapic->svr &= ~APIC_SVR_ENABLE;
625
626         /* data returned to BSP */
627         cpu_apic_versions[0] = lapic->version;
628 }
629
630 /*******************************************************************
631  * local functions and data
632  */
633
634 /*
635  * start the SMP system
636  */
637 static void
638 mp_enable(u_int boot_addr)
639 {
640         POSTCODE(MP_ENABLE_POST);
641
642         lapic_config();
643
644         /* Initialize BSP's local APIC */
645         lapic_init(TRUE);
646
647         /* start each Application Processor */
648         start_all_aps(boot_addr);
649
650         if (apic_io_enable)
651                 ioapic_config();
652
653         /* Finalize PIC */
654         MachIntrABI.finalize();
655 }
656
657
658 /*
659  * look for the MP spec signature
660  */
661
662 /* string defined by the Intel MP Spec as identifying the MP table */
663 #define MP_SIG          0x5f504d5f      /* _MP_ */
664 #define NEXT(X)         ((X) += 4)
665 static long
666 mptable_search_sig(u_int32_t target, int count)
667 {
668         vm_size_t map_size;
669         u_int32_t *addr;
670         int x, ret;
671
672         KKASSERT(target != 0);
673
674         map_size = count * sizeof(u_int32_t);
675         addr = pmap_mapdev((vm_paddr_t)target, map_size);
676
677         ret = 0;
678         for (x = 0; x < count; NEXT(x)) {
679                 if (addr[x] == MP_SIG) {
680                         /* make array index a byte index */
681                         ret = target + (x * sizeof(u_int32_t));
682                         break;
683                 }
684         }
685
686         pmap_unmapdev((vm_offset_t)addr, map_size);
687         return ret;
688 }
689
690 static int processor_entry      (const struct PROCENTRY *entry, int cpu);
691
692 /*
693  * Check if we should perform a hyperthreading "fix-up" to
694  * enumerate any logical CPU's that aren't already listed
695  * in the table.
696  *
697  * XXX: We assume that all of the physical CPUs in the
698  * system have the same number of logical CPUs.
699  *
700  * XXX: We assume that APIC ID's are allocated such that
701  * the APIC ID's for a physical processor are aligned
702  * with the number of logical CPU's in the processor.
703  */
704 static int
705 mptable_hyperthread_fixup(cpumask_t id_mask, int cpu_count)
706 {
707         int i, id, lcpus_max, logical_cpus;
708
709         if ((cpu_feature & CPUID_HTT) == 0)
710                 return 0;
711
712         lcpus_max = (cpu_procinfo & CPUID_HTT_CORES) >> 16;
713         if (lcpus_max <= 1)
714                 return 0;
715
716         if (strcmp(cpu_vendor, "GenuineIntel") == 0) {
717                 /*
718                  * INSTRUCTION SET REFERENCE, A-M (#253666)
719                  * Page 3-181, Table 3-20
720                  * "The nearest power-of-2 integer that is not smaller
721                  *  than EBX[23:16] is the number of unique initial APIC
722                  *  IDs reserved for addressing different logical
723                  *  processors in a physical package."
724                  */
725                 for (i = 0; ; ++i) {
726                         if ((1 << i) >= lcpus_max) {
727                                 lcpus_max = 1 << i;
728                                 break;
729                         }
730                 }
731         }
732
733         KKASSERT(cpu_count != 0);
734         if (cpu_count == lcpus_max) {
735                 /* We have nothing to fix */
736                 return 0;
737         } else if (cpu_count == 1) {
738                 /* XXX this may be incorrect */
739                 logical_cpus = lcpus_max;
740         } else {
741                 int cur, prev, dist;
742
743                 /*
744                  * Calculate the distances between two nearest
745                  * APIC IDs.  If all such distances are same,
746                  * then it is the number of missing cpus that
747                  * we are going to fill later.
748                  */
749                 dist = cur = prev = -1;
750                 for (id = 0; id < MAXCPU; ++id) {
751                         if ((id_mask & CPUMASK(id)) == 0)
752                                 continue;
753
754                         cur = id;
755                         if (prev >= 0) {
756                                 int new_dist = cur - prev;
757
758                                 if (dist < 0)
759                                         dist = new_dist;
760
761                                 /*
762                                  * Make sure that all distances
763                                  * between two nearest APIC IDs
764                                  * are same.
765                                  */
766                                 if (dist != new_dist)
767                                         return 0;
768                         }
769                         prev = cur;
770                 }
771                 if (dist == 1)
772                         return 0;
773
774                 /* Must be power of 2 */
775                 if (dist & (dist - 1))
776                         return 0;
777
778                 /* Can't exceed CPU package capacity */
779                 if (dist > lcpus_max)
780                         logical_cpus = lcpus_max;
781                 else
782                         logical_cpus = dist;
783         }
784
785         /*
786          * For each APIC ID of a CPU that is set in the mask,
787          * scan the other candidate APIC ID's for this
788          * physical processor.  If any of those ID's are
789          * already in the table, then kill the fixup.
790          */
791         for (id = 0; id < MAXCPU; id++) {
792                 if ((id_mask & CPUMASK(id)) == 0)
793                         continue;
794                 /* First, make sure we are on a logical_cpus boundary. */
795                 if (id % logical_cpus != 0)
796                         return 0;
797                 for (i = id + 1; i < id + logical_cpus; i++)
798                         if ((id_mask & CPUMASK(i)) != 0)
799                                 return 0;
800         }
801         return logical_cpus;
802 }
803
804 static int
805 mptable_map(struct mptable_pos *mpt)
806 {
807         mpfps_t fps = NULL;
808         mpcth_t cth = NULL;
809         vm_size_t cth_mapsz = 0;
810
811         KKASSERT(mptable_fps_phyaddr != 0);
812
813         bzero(mpt, sizeof(*mpt));
814
815         fps = pmap_mapdev(mptable_fps_phyaddr, sizeof(*fps));
816         if (fps->pap != 0) {
817                 /*
818                  * Map configuration table header to get
819                  * the base table size
820                  */
821                 cth = pmap_mapdev(fps->pap, sizeof(*cth));
822                 cth_mapsz = cth->base_table_length;
823                 pmap_unmapdev((vm_offset_t)cth, sizeof(*cth));
824
825                 if (cth_mapsz < sizeof(*cth)) {
826                         kprintf("invalid base MP table length %d\n",
827                                 (int)cth_mapsz);
828                         pmap_unmapdev((vm_offset_t)fps, sizeof(*fps));
829                         return EINVAL;
830                 }
831
832                 /*
833                  * Map the base table
834                  */
835                 cth = pmap_mapdev(fps->pap, cth_mapsz);
836         }
837
838         mpt->mp_fps = fps;
839         mpt->mp_cth = cth;
840         mpt->mp_cth_mapsz = cth_mapsz;
841
842         return 0;
843 }
844
845 static void
846 mptable_unmap(struct mptable_pos *mpt)
847 {
848         if (mpt->mp_cth != NULL) {
849                 pmap_unmapdev((vm_offset_t)mpt->mp_cth, mpt->mp_cth_mapsz);
850                 mpt->mp_cth = NULL;
851                 mpt->mp_cth_mapsz = 0;
852         }
853         if (mpt->mp_fps != NULL) {
854                 pmap_unmapdev((vm_offset_t)mpt->mp_fps, sizeof(*mpt->mp_fps));
855                 mpt->mp_fps = NULL;
856         }
857 }
858
859 void
860 mp_set_cpuids(int cpu_id, int apic_id)
861 {
862         CPU_TO_ID(cpu_id) = apic_id;
863         ID_TO_CPU(apic_id) = cpu_id;
864 }
865
866 static int
867 processor_entry(const struct PROCENTRY *entry, int cpu)
868 {
869         KKASSERT(cpu > 0);
870
871         /* check for usability */
872         if (!(entry->cpu_flags & PROCENTRY_FLAG_EN))
873                 return 0;
874
875         /* check for BSP flag */
876         if (entry->cpu_flags & PROCENTRY_FLAG_BP) {
877                 mp_set_cpuids(0, entry->apic_id);
878                 return 0;       /* its already been counted */
879         }
880
881         /* add another AP to list, if less than max number of CPUs */
882         else if (cpu < MAXCPU) {
883                 mp_set_cpuids(cpu, entry->apic_id);
884                 return 1;
885         }
886
887         return 0;
888 }
889
890 /*
891  * Map a physical memory address representing I/O into KVA.  The I/O
892  * block is assumed not to cross a page boundary.
893  */
894 void *
895 ioapic_map(vm_paddr_t pa)
896 {
897         KKASSERT(pa < 0x100000000LL);
898
899         return pmap_mapdev_uncacheable(pa, PAGE_SIZE);
900 }
901
902 /*
903  * start each AP in our list
904  */
905 static int
906 start_all_aps(u_int boot_addr)
907 {
908         vm_offset_t va = boot_address + KERNBASE;
909         u_int64_t *pt4, *pt3, *pt2;
910         int     x, i, pg;
911         int     shift;
912         int     smicount;
913         int     smibest;
914         int     smilast;
915         u_char  mpbiosreason;
916         u_long  mpbioswarmvec;
917         struct mdglobaldata *gd;
918         struct privatespace *ps;
919
920         POSTCODE(START_ALL_APS_POST);
921
922         /* install the AP 1st level boot code */
923         pmap_kenter(va, boot_address);
924         cpu_invlpg((void *)va);         /* JG XXX */
925         bcopy(mptramp_start, (void *)va, bootMP_size);
926
927         /* Locate the page tables, they'll be below the trampoline */
928         pt4 = (u_int64_t *)(uintptr_t)(mptramp_pagetables + KERNBASE);
929         pt3 = pt4 + (PAGE_SIZE) / sizeof(u_int64_t);
930         pt2 = pt3 + (PAGE_SIZE) / sizeof(u_int64_t);
931
932         /* Create the initial 1GB replicated page tables */
933         for (i = 0; i < 512; i++) {
934                 /* Each slot of the level 4 pages points to the same level 3 page */
935                 pt4[i] = (u_int64_t)(uintptr_t)(mptramp_pagetables + PAGE_SIZE);
936                 pt4[i] |= PG_V | PG_RW | PG_U;
937
938                 /* Each slot of the level 3 pages points to the same level 2 page */
939                 pt3[i] = (u_int64_t)(uintptr_t)(mptramp_pagetables + (2 * PAGE_SIZE));
940                 pt3[i] |= PG_V | PG_RW | PG_U;
941
942                 /* The level 2 page slots are mapped with 2MB pages for 1GB. */
943                 pt2[i] = i * (2 * 1024 * 1024);
944                 pt2[i] |= PG_V | PG_RW | PG_PS | PG_U;
945         }
946
947         /* save the current value of the warm-start vector */
948         mpbioswarmvec = *((u_int32_t *) WARMBOOT_OFF);
949         outb(CMOS_REG, BIOS_RESET);
950         mpbiosreason = inb(CMOS_DATA);
951
952         /* setup a vector to our boot code */
953         *((volatile u_short *) WARMBOOT_OFF) = WARMBOOT_TARGET;
954         *((volatile u_short *) WARMBOOT_SEG) = (boot_address >> 4);
955         outb(CMOS_REG, BIOS_RESET);
956         outb(CMOS_DATA, BIOS_WARM);     /* 'warm-start' */
957
958         /*
959          * If we have a TSC we can figure out the SMI interrupt rate.
960          * The SMI does not necessarily use a constant rate.  Spend
961          * up to 250ms trying to figure it out.
962          */
963         smibest = 0;
964         if (cpu_feature & CPUID_TSC) {
965                 set_apic_timer(275000);
966                 smilast = read_apic_timer();
967                 for (x = 0; x < 20 && read_apic_timer(); ++x) {
968                         smicount = smitest();
969                         if (smibest == 0 || smilast - smicount < smibest)
970                                 smibest = smilast - smicount;
971                         smilast = smicount;
972                 }
973                 if (smibest > 250000)
974                         smibest = 0;
975                 if (smibest) {
976                         smibest = smibest * (int64_t)1000000 /
977                                   get_apic_timer_frequency();
978                 }
979         }
980         if (smibest)
981                 kprintf("SMI Frequency (worst case): %d Hz (%d us)\n",
982                         1000000 / smibest, smibest);
983
984         /* start each AP */
985         for (x = 1; x <= mp_naps; ++x) {
986
987                 /* This is a bit verbose, it will go away soon.  */
988
989                 /* first page of AP's private space */
990                 pg = x * x86_64_btop(sizeof(struct privatespace));
991
992                 /* allocate new private data page(s) */
993                 gd = (struct mdglobaldata *)kmem_alloc(&kernel_map, 
994                                 MDGLOBALDATA_BASEALLOC_SIZE);
995
996                 gd = &CPU_prvspace[x].mdglobaldata;     /* official location */
997                 bzero(gd, sizeof(*gd));
998                 gd->mi.gd_prvspace = ps = &CPU_prvspace[x];
999
1000                 /* prime data page for it to use */
1001                 mi_gdinit(&gd->mi, x);
1002                 cpu_gdinit(gd, x);
1003                 gd->mi.gd_ipiq = (void *)kmem_alloc(&kernel_map, sizeof(lwkt_ipiq) * (mp_naps + 1));
1004                 bzero(gd->mi.gd_ipiq, sizeof(lwkt_ipiq) * (mp_naps + 1));
1005
1006                 /* setup a vector to our boot code */
1007                 *((volatile u_short *) WARMBOOT_OFF) = WARMBOOT_TARGET;
1008                 *((volatile u_short *) WARMBOOT_SEG) = (boot_addr >> 4);
1009                 outb(CMOS_REG, BIOS_RESET);
1010                 outb(CMOS_DATA, BIOS_WARM);     /* 'warm-start' */
1011
1012                 /*
1013                  * Setup the AP boot stack
1014                  */
1015                 bootSTK = &ps->idlestack[UPAGES*PAGE_SIZE/2];
1016                 bootAP = x;
1017
1018                 /* attempt to start the Application Processor */
1019                 CHECK_INIT(99); /* setup checkpoints */
1020                 if (!start_ap(gd, boot_addr, smibest)) {
1021                         kprintf("\nAP #%d (PHY# %d) failed!\n",
1022                                 x, CPU_TO_ID(x));
1023                         CHECK_PRINT("trace");   /* show checkpoints */
1024                         /* better panic as the AP may be running loose */
1025                         kprintf("panic y/n? [y] ");
1026                         if (cngetc() != 'n')
1027                                 panic("bye-bye");
1028                 }
1029                 CHECK_PRINT("trace");           /* show checkpoints */
1030
1031                 /* record its version info */
1032                 cpu_apic_versions[x] = cpu_apic_versions[0];
1033         }
1034
1035         /* set ncpus to 1 + highest logical cpu.  Not all may have come up */
1036         ncpus = x;
1037
1038         /* ncpus2 -- ncpus rounded down to the nearest power of 2 */
1039         for (shift = 0; (1 << shift) <= ncpus; ++shift)
1040                 ;
1041         --shift;
1042         ncpus2_shift = shift;
1043         ncpus2 = 1 << shift;
1044         ncpus2_mask = ncpus2 - 1;
1045
1046         /* ncpus_fit -- ncpus rounded up to the nearest power of 2 */
1047         if ((1 << shift) < ncpus)
1048                 ++shift;
1049         ncpus_fit = 1 << shift;
1050         ncpus_fit_mask = ncpus_fit - 1;
1051
1052         /* build our map of 'other' CPUs */
1053         mycpu->gd_other_cpus = smp_startup_mask & ~CPUMASK(mycpu->gd_cpuid);
1054         mycpu->gd_ipiq = (void *)kmem_alloc(&kernel_map, sizeof(lwkt_ipiq) * ncpus);
1055         bzero(mycpu->gd_ipiq, sizeof(lwkt_ipiq) * ncpus);
1056
1057         /* fill in our (BSP) APIC version */
1058         cpu_apic_versions[0] = lapic->version;
1059
1060         /* restore the warmstart vector */
1061         *(u_long *) WARMBOOT_OFF = mpbioswarmvec;
1062         outb(CMOS_REG, BIOS_RESET);
1063         outb(CMOS_DATA, mpbiosreason);
1064
1065         /*
1066          * NOTE!  The idlestack for the BSP was setup by locore.  Finish
1067          * up, clean out the P==V mapping we did earlier.
1068          */
1069         pmap_set_opt();
1070
1071         /*
1072          * Wait all APs to finish initializing LAPIC
1073          */
1074         mp_finish_lapic = 1;
1075         if (bootverbose)
1076                 kprintf("SMP: Waiting APs LAPIC initialization\n");
1077         if (cpu_feature & CPUID_TSC)
1078                 tsc0_offset = rdtsc();
1079         tsc_offsets[0] = 0;
1080         rel_mplock();
1081         while (smp_lapic_mask != smp_startup_mask) {
1082                 cpu_lfence();
1083                 if (cpu_feature & CPUID_TSC)
1084                         tsc0_offset = rdtsc();
1085         }
1086         while (try_mplock() == 0)
1087                 ;
1088
1089         /* number of APs actually started */
1090         return ncpus - 1;
1091 }
1092
1093
1094 /*
1095  * load the 1st level AP boot code into base memory.
1096  */
1097
1098 /* targets for relocation */
1099 extern void bigJump(void);
1100 extern void bootCodeSeg(void);
1101 extern void bootDataSeg(void);
1102 extern void MPentry(void);
1103 extern u_int MP_GDT;
1104 extern u_int mp_gdtbase;
1105
1106 #if 0
1107
1108 static void
1109 install_ap_tramp(u_int boot_addr)
1110 {
1111         int     x;
1112         int     size = *(int *) ((u_long) & bootMP_size);
1113         u_char *src = (u_char *) ((u_long) bootMP);
1114         u_char *dst = (u_char *) boot_addr + KERNBASE;
1115         u_int   boot_base = (u_int) bootMP;
1116         u_int8_t *dst8;
1117         u_int16_t *dst16;
1118         u_int32_t *dst32;
1119
1120         POSTCODE(INSTALL_AP_TRAMP_POST);
1121
1122         for (x = 0; x < size; ++x)
1123                 *dst++ = *src++;
1124
1125         /*
1126          * modify addresses in code we just moved to basemem. unfortunately we
1127          * need fairly detailed info about mpboot.s for this to work.  changes
1128          * to mpboot.s might require changes here.
1129          */
1130
1131         /* boot code is located in KERNEL space */
1132         dst = (u_char *) boot_addr + KERNBASE;
1133
1134         /* modify the lgdt arg */
1135         dst32 = (u_int32_t *) (dst + ((u_int) & mp_gdtbase - boot_base));
1136         *dst32 = boot_addr + ((u_int) & MP_GDT - boot_base);
1137
1138         /* modify the ljmp target for MPentry() */
1139         dst32 = (u_int32_t *) (dst + ((u_int) bigJump - boot_base) + 1);
1140         *dst32 = ((u_int) MPentry - KERNBASE);
1141
1142         /* modify the target for boot code segment */
1143         dst16 = (u_int16_t *) (dst + ((u_int) bootCodeSeg - boot_base));
1144         dst8 = (u_int8_t *) (dst16 + 1);
1145         *dst16 = (u_int) boot_addr & 0xffff;
1146         *dst8 = ((u_int) boot_addr >> 16) & 0xff;
1147
1148         /* modify the target for boot data segment */
1149         dst16 = (u_int16_t *) (dst + ((u_int) bootDataSeg - boot_base));
1150         dst8 = (u_int8_t *) (dst16 + 1);
1151         *dst16 = (u_int) boot_addr & 0xffff;
1152         *dst8 = ((u_int) boot_addr >> 16) & 0xff;
1153 }
1154
1155 #endif
1156
1157 /*
1158  * This function starts the AP (application processor) identified
1159  * by the APIC ID 'physicalCpu'.  It does quite a "song and dance"
1160  * to accomplish this.  This is necessary because of the nuances
1161  * of the different hardware we might encounter.  It ain't pretty,
1162  * but it seems to work.
1163  *
1164  * NOTE: eventually an AP gets to ap_init(), which is called just 
1165  * before the AP goes into the LWKT scheduler's idle loop.
1166  */
1167 static int
1168 start_ap(struct mdglobaldata *gd, u_int boot_addr, int smibest)
1169 {
1170         int     physical_cpu;
1171         int     vector;
1172         u_long  icr_lo, icr_hi;
1173
1174         POSTCODE(START_AP_POST);
1175
1176         /* get the PHYSICAL APIC ID# */
1177         physical_cpu = CPU_TO_ID(gd->mi.gd_cpuid);
1178
1179         /* calculate the vector */
1180         vector = (boot_addr >> 12) & 0xff;
1181
1182         /* We don't want anything interfering */
1183         cpu_disable_intr();
1184
1185         /* Make sure the target cpu sees everything */
1186         wbinvd();
1187
1188         /*
1189          * Try to detect when a SMI has occurred, wait up to 200ms.
1190          *
1191          * If a SMI occurs during an AP reset but before we issue
1192          * the STARTUP command, the AP may brick.  To work around
1193          * this problem we hold off doing the AP startup until
1194          * after we have detected the SMI.  Hopefully another SMI
1195          * will not occur before we finish the AP startup.
1196          *
1197          * Retries don't seem to help.  SMIs have a window of opportunity
1198          * and if USB->legacy keyboard emulation is enabled in the BIOS
1199          * the interrupt rate can be quite high.
1200          *
1201          * NOTE: Don't worry about the L1 cache load, it might bloat
1202          *       ldelta a little but ndelta will be so huge when the SMI
1203          *       occurs the detection logic will still work fine.
1204          */
1205         if (smibest) {
1206                 set_apic_timer(200000);
1207                 smitest();
1208         }
1209
1210         /*
1211          * first we do an INIT/RESET IPI this INIT IPI might be run, reseting
1212          * and running the target CPU. OR this INIT IPI might be latched (P5
1213          * bug), CPU waiting for STARTUP IPI. OR this INIT IPI might be
1214          * ignored.
1215          *
1216          * see apic/apicreg.h for icr bit definitions.
1217          *
1218          * TIME CRITICAL CODE, DO NOT DO ANY KPRINTFS IN THE HOT PATH.
1219          */
1220
1221         /*
1222          * Setup the address for the target AP.  We can setup
1223          * icr_hi once and then just trigger operations with
1224          * icr_lo.
1225          */
1226         icr_hi = lapic->icr_hi & ~APIC_ID_MASK;
1227         icr_hi |= (physical_cpu << 24);
1228         icr_lo = lapic->icr_lo & 0xfff00000;
1229         lapic->icr_hi = icr_hi;
1230
1231         /*
1232          * Do an INIT IPI: assert RESET
1233          *
1234          * Use edge triggered mode to assert INIT
1235          */
1236         lapic->icr_lo = icr_lo | 0x00004500;
1237         while (lapic->icr_lo & APIC_DELSTAT_MASK)
1238                  /* spin */ ;
1239
1240         /*
1241          * The spec calls for a 10ms delay but we may have to use a
1242          * MUCH lower delay to avoid bricking an AP due to a fast SMI
1243          * interrupt.  We have other loops here too and dividing by 2
1244          * doesn't seem to be enough even after subtracting 350us,
1245          * so we divide by 4.
1246          *
1247          * Our minimum delay is 150uS, maximum is 10ms.  If no SMI
1248          * interrupt was detected we use the full 10ms.
1249          */
1250         if (smibest == 0)
1251                 u_sleep(10000);
1252         else if (smibest < 150 * 4 + 350)
1253                 u_sleep(150);
1254         else if ((smibest - 350) / 4 < 10000)
1255                 u_sleep((smibest - 350) / 4);
1256         else
1257                 u_sleep(10000);
1258
1259         /*
1260          * Do an INIT IPI: deassert RESET
1261          *
1262          * Use level triggered mode to deassert.  It is unclear
1263          * why we need to do this.
1264          */
1265         lapic->icr_lo = icr_lo | 0x00008500;
1266         while (lapic->icr_lo & APIC_DELSTAT_MASK)
1267                  /* spin */ ;
1268         u_sleep(150);                           /* wait 150us */
1269
1270         /*
1271          * Next we do a STARTUP IPI: the previous INIT IPI might still be
1272          * latched, (P5 bug) this 1st STARTUP would then terminate
1273          * immediately, and the previously started INIT IPI would continue. OR
1274          * the previous INIT IPI has already run. and this STARTUP IPI will
1275          * run. OR the previous INIT IPI was ignored. and this STARTUP IPI
1276          * will run.
1277          */
1278         lapic->icr_lo = icr_lo | 0x00000600 | vector;
1279         while (lapic->icr_lo & APIC_DELSTAT_MASK)
1280                  /* spin */ ;
1281         u_sleep(200);           /* wait ~200uS */
1282
1283         /*
1284          * Finally we do a 2nd STARTUP IPI: this 2nd STARTUP IPI should run IF
1285          * the previous STARTUP IPI was cancelled by a latched INIT IPI. OR
1286          * this STARTUP IPI will be ignored, as only ONE STARTUP IPI is
1287          * recognized after hardware RESET or INIT IPI.
1288          */
1289         lapic->icr_lo = icr_lo | 0x00000600 | vector;
1290         while (lapic->icr_lo & APIC_DELSTAT_MASK)
1291                  /* spin */ ;
1292
1293         /* Resume normal operation */
1294         cpu_enable_intr();
1295
1296         /* wait for it to start, see ap_init() */
1297         set_apic_timer(5000000);/* == 5 seconds */
1298         while (read_apic_timer()) {
1299                 if (smp_startup_mask & CPUMASK(gd->mi.gd_cpuid))
1300                         return 1;       /* return SUCCESS */
1301         }
1302
1303         return 0;               /* return FAILURE */
1304 }
1305
1306 static
1307 int
1308 smitest(void)
1309 {
1310         int64_t ltsc;
1311         int64_t ntsc;
1312         int64_t ldelta;
1313         int64_t ndelta;
1314         int count;
1315
1316         ldelta = 0;
1317         ndelta = 0;
1318         while (read_apic_timer()) {
1319                 ltsc = rdtsc();
1320                 for (count = 0; count < 100; ++count)
1321                         ntsc = rdtsc(); /* force loop to occur */
1322                 if (ldelta) {
1323                         ndelta = ntsc - ltsc;
1324                         if (ldelta > ndelta)
1325                                 ldelta = ndelta;
1326                         if (ndelta > ldelta * 2)
1327                                 break;
1328                 } else {
1329                         ldelta = ntsc - ltsc;
1330                 }
1331         }
1332         return(read_apic_timer());
1333 }
1334
1335 /*
1336  * Synchronously flush the TLB on all other CPU's.  The current cpu's
1337  * TLB is not flushed.  If the caller wishes to flush the current cpu's
1338  * TLB the caller must call cpu_invltlb() in addition to smp_invltlb().
1339  *
1340  * NOTE: If for some reason we were unable to start all cpus we cannot
1341  *       safely use broadcast IPIs.
1342  */
1343
1344 static cpumask_t smp_invltlb_req;
1345
1346 #define SMP_INVLTLB_DEBUG
1347
1348 void
1349 smp_invltlb(void)
1350 {
1351 #ifdef SMP
1352         struct mdglobaldata *md = mdcpu;
1353 #ifdef SMP_INVLTLB_DEBUG
1354         long count = 0;
1355         long xcount = 0;
1356 #endif
1357
1358         crit_enter_gd(&md->mi);
1359         md->gd_invltlb_ret = 0;
1360         ++md->mi.gd_cnt.v_smpinvltlb;
1361         atomic_set_cpumask(&smp_invltlb_req, md->mi.gd_cpumask);
1362 #ifdef SMP_INVLTLB_DEBUG
1363 again:
1364 #endif
1365         if (smp_startup_mask == smp_active_mask) {
1366                 all_but_self_ipi(XINVLTLB_OFFSET);
1367         } else {
1368                 selected_apic_ipi(smp_active_mask & ~md->mi.gd_cpumask,
1369                                   XINVLTLB_OFFSET, APIC_DELMODE_FIXED);
1370         }
1371
1372 #ifdef SMP_INVLTLB_DEBUG
1373         if (xcount)
1374                 kprintf("smp_invltlb: ipi sent\n");
1375 #endif
1376         while ((md->gd_invltlb_ret & smp_active_mask & ~md->mi.gd_cpumask) !=
1377                (smp_active_mask & ~md->mi.gd_cpumask)) {
1378                 cpu_mfence();
1379                 cpu_pause();
1380 #ifdef SMP_INVLTLB_DEBUG
1381                 /* DEBUGGING */
1382                 if (++count == 400000000) {
1383                         print_backtrace(-1);
1384                         kprintf("smp_invltlb: endless loop %08lx %08lx, "
1385                                 "rflags %016jx retry",
1386                               (long)md->gd_invltlb_ret,
1387                               (long)smp_invltlb_req,
1388                               (intmax_t)read_rflags());
1389                         __asm __volatile ("sti");
1390                         ++xcount;
1391                         if (xcount > 2)
1392                                 lwkt_process_ipiq();
1393                         if (xcount > 3) {
1394                                 int bcpu = BSFCPUMASK(~md->gd_invltlb_ret &
1395                                                       ~md->mi.gd_cpumask &
1396                                                       smp_active_mask);
1397                                 globaldata_t xgd;
1398
1399                                 kprintf("bcpu %d\n", bcpu);
1400                                 xgd = globaldata_find(bcpu);
1401                                 kprintf("thread %p %s\n", xgd->gd_curthread, xgd->gd_curthread->td_comm);
1402                         }
1403                         if (xcount > 5)
1404                                 Debugger("giving up");
1405                         count = 0;
1406                         goto again;
1407                 }
1408 #endif
1409         }
1410         atomic_clear_cpumask(&smp_invltlb_req, md->mi.gd_cpumask);
1411         crit_exit_gd(&md->mi);
1412 #endif
1413 }
1414
1415 #ifdef SMP
1416
1417 /*
1418  * Called from Xinvltlb assembly with interrupts disabled.  We didn't
1419  * bother to bump the critical section count or nested interrupt count
1420  * so only do very low level operations here.
1421  */
1422 void
1423 smp_invltlb_intr(void)
1424 {
1425         struct mdglobaldata *md = mdcpu;
1426         struct mdglobaldata *omd;
1427         cpumask_t mask;
1428         int cpu;
1429
1430         cpu_mfence();
1431         mask = smp_invltlb_req;
1432         cpu_invltlb();
1433         while (mask) {
1434                 cpu = BSFCPUMASK(mask);
1435                 mask &= ~CPUMASK(cpu);
1436                 omd = (struct mdglobaldata *)globaldata_find(cpu);
1437                 atomic_set_cpumask(&omd->gd_invltlb_ret, md->mi.gd_cpumask);
1438         }
1439 }
1440
1441 #endif
1442
1443 /*
1444  * When called the executing CPU will send an IPI to all other CPUs
1445  *  requesting that they halt execution.
1446  *
1447  * Usually (but not necessarily) called with 'other_cpus' as its arg.
1448  *
1449  *  - Signals all CPUs in map to stop.
1450  *  - Waits for each to stop.
1451  *
1452  * Returns:
1453  *  -1: error
1454  *   0: NA
1455  *   1: ok
1456  *
1457  * XXX FIXME: this is not MP-safe, needs a lock to prevent multiple CPUs
1458  *            from executing at same time.
1459  */
1460 int
1461 stop_cpus(cpumask_t map)
1462 {
1463         map &= smp_active_mask;
1464
1465         /* send the Xcpustop IPI to all CPUs in map */
1466         selected_apic_ipi(map, XCPUSTOP_OFFSET, APIC_DELMODE_FIXED);
1467         
1468         while ((stopped_cpus & map) != map)
1469                 /* spin */ ;
1470
1471         return 1;
1472 }
1473
1474
1475 /*
1476  * Called by a CPU to restart stopped CPUs. 
1477  *
1478  * Usually (but not necessarily) called with 'stopped_cpus' as its arg.
1479  *
1480  *  - Signals all CPUs in map to restart.
1481  *  - Waits for each to restart.
1482  *
1483  * Returns:
1484  *  -1: error
1485  *   0: NA
1486  *   1: ok
1487  */
1488 int
1489 restart_cpus(cpumask_t map)
1490 {
1491         /* signal other cpus to restart */
1492         started_cpus = map & smp_active_mask;
1493
1494         while ((stopped_cpus & map) != 0) /* wait for each to clear its bit */
1495                 /* spin */ ;
1496
1497         return 1;
1498 }
1499
1500 /*
1501  * This is called once the mpboot code has gotten us properly relocated
1502  * and the MMU turned on, etc.   ap_init() is actually the idle thread,
1503  * and when it returns the scheduler will call the real cpu_idle() main
1504  * loop for the idlethread.  Interrupts are disabled on entry and should
1505  * remain disabled at return.
1506  */
1507 void
1508 ap_init(void)
1509 {
1510         u_int   apic_id;
1511
1512         /*
1513          * Adjust smp_startup_mask to signal the BSP that we have started
1514          * up successfully.  Note that we do not yet hold the BGL.  The BSP
1515          * is waiting for our signal.
1516          *
1517          * We can't set our bit in smp_active_mask yet because we are holding
1518          * interrupts physically disabled and remote cpus could deadlock
1519          * trying to send us an IPI.
1520          */
1521         smp_startup_mask |= CPUMASK(mycpu->gd_cpuid);
1522         cpu_mfence();
1523
1524         /*
1525          * Interlock for LAPIC initialization.  Wait until mp_finish_lapic is
1526          * non-zero, then get the MP lock.
1527          *
1528          * Note: We are in a critical section.
1529          *
1530          * Note: we are the idle thread, we can only spin.
1531          *
1532          * Note: The load fence is memory volatile and prevents the compiler
1533          * from improperly caching mp_finish_lapic, and the cpu from improperly
1534          * caching it.
1535          */
1536         while (mp_finish_lapic == 0)
1537                 cpu_lfence();
1538         while (try_mplock() == 0)
1539                 ;
1540
1541         if (cpu_feature & CPUID_TSC) {
1542                 /*
1543                  * The BSP is constantly updating tsc0_offset, figure out
1544                  * the relative difference to synchronize ktrdump.
1545                  */
1546                 tsc_offsets[mycpu->gd_cpuid] = rdtsc() - tsc0_offset;
1547         }
1548
1549         /* BSP may have changed PTD while we're waiting for the lock */
1550         cpu_invltlb();
1551
1552         /* Build our map of 'other' CPUs. */
1553         mycpu->gd_other_cpus = smp_startup_mask & ~CPUMASK(mycpu->gd_cpuid);
1554
1555         /* A quick check from sanity claus */
1556         apic_id = (apic_id_to_logical[(lapic->id & 0xff000000) >> 24]);
1557         if (mycpu->gd_cpuid != apic_id) {
1558                 kprintf("SMP: cpuid = %d\n", mycpu->gd_cpuid);
1559                 kprintf("SMP: apic_id = %d lapicid %d\n",
1560                         apic_id, (lapic->id & 0xff000000) >> 24);
1561 #if JGXXX
1562                 kprintf("PTD[MPPTDI] = %p\n", (void *)PTD[MPPTDI]);
1563 #endif
1564                 panic("cpuid mismatch! boom!!");
1565         }
1566
1567         /* Initialize AP's local APIC for irq's */
1568         lapic_init(FALSE);
1569
1570         /* LAPIC initialization is done */
1571         smp_lapic_mask |= CPUMASK(mycpu->gd_cpuid);
1572         cpu_mfence();
1573
1574         /* Let BSP move onto the next initialization stage */
1575         rel_mplock();
1576
1577         /*
1578          * Interlock for finalization.  Wait until mp_finish is non-zero,
1579          * then get the MP lock.
1580          *
1581          * Note: We are in a critical section.
1582          *
1583          * Note: we are the idle thread, we can only spin.
1584          *
1585          * Note: The load fence is memory volatile and prevents the compiler
1586          * from improperly caching mp_finish, and the cpu from improperly
1587          * caching it.
1588          */
1589         while (mp_finish == 0)
1590                 cpu_lfence();
1591         while (try_mplock() == 0)
1592                 ;
1593
1594         /* BSP may have changed PTD while we're waiting for the lock */
1595         cpu_invltlb();
1596
1597         /* Set memory range attributes for this CPU to match the BSP */
1598         mem_range_AP_init();
1599
1600         /*
1601          * Once we go active we must process any IPIQ messages that may
1602          * have been queued, because no actual IPI will occur until we
1603          * set our bit in the smp_active_mask.  If we don't the IPI
1604          * message interlock could be left set which would also prevent
1605          * further IPIs.
1606          *
1607          * The idle loop doesn't expect the BGL to be held and while
1608          * lwkt_switch() normally cleans things up this is a special case
1609          * because we returning almost directly into the idle loop.
1610          *
1611          * The idle thread is never placed on the runq, make sure
1612          * nothing we've done put it there.
1613          */
1614         KKASSERT(get_mplock_count(curthread) == 1);
1615         smp_active_mask |= CPUMASK(mycpu->gd_cpuid);
1616
1617         /*
1618          * Enable interrupts here.  idle_restore will also do it, but
1619          * doing it here lets us clean up any strays that got posted to
1620          * the CPU during the AP boot while we are still in a critical
1621          * section.
1622          */
1623         __asm __volatile("sti; pause; pause"::);
1624         bzero(mdcpu->gd_ipending, sizeof(mdcpu->gd_ipending));
1625
1626         initclocks_pcpu();      /* clock interrupts (via IPIs) */
1627         lwkt_process_ipiq();
1628
1629         /*
1630          * Releasing the mp lock lets the BSP finish up the SMP init
1631          */
1632         rel_mplock();
1633         KKASSERT((curthread->td_flags & TDF_RUNQ) == 0);
1634 }
1635
1636 /*
1637  * Get SMP fully working before we start initializing devices.
1638  */
1639 static
1640 void
1641 ap_finish(void)
1642 {
1643         mp_finish = 1;
1644         if (bootverbose)
1645                 kprintf("Finish MP startup\n");
1646         rel_mplock();
1647         while (smp_active_mask != smp_startup_mask)
1648                 cpu_lfence();
1649         while (try_mplock() == 0)
1650                 ;
1651         if (bootverbose) {
1652                 kprintf("Active CPU Mask: %016jx\n",
1653                         (uintmax_t)smp_active_mask);
1654         }
1655 }
1656
1657 SYSINIT(finishsmp, SI_BOOT2_FINISH_SMP, SI_ORDER_FIRST, ap_finish, NULL)
1658
1659 void
1660 cpu_send_ipiq(int dcpu)
1661 {
1662         if (CPUMASK(dcpu) & smp_active_mask)
1663                 single_apic_ipi(dcpu, XIPIQ_OFFSET, APIC_DELMODE_FIXED);
1664 }
1665
1666 #if 0   /* single_apic_ipi_passive() not working yet */
1667 /*
1668  * Returns 0 on failure, 1 on success
1669  */
1670 int
1671 cpu_send_ipiq_passive(int dcpu)
1672 {
1673         int r = 0;
1674         if (CPUMASK(dcpu) & smp_active_mask) {
1675                 r = single_apic_ipi_passive(dcpu, XIPIQ_OFFSET,
1676                                         APIC_DELMODE_FIXED);
1677         }
1678         return(r);
1679 }
1680 #endif
1681
1682 static int
1683 mptable_bus_info_callback(void *xarg, const void *pos, int type)
1684 {
1685         struct mptable_bus_info *bus_info = xarg;
1686         const struct BUSENTRY *ent;
1687         struct mptable_bus *bus;
1688
1689         if (type != 1)
1690                 return 0;
1691
1692         ent = pos;
1693         TAILQ_FOREACH(bus, &bus_info->mbi_list, mb_link) {
1694                 if (bus->mb_id == ent->bus_id) {
1695                         kprintf("mptable_bus_info_alloc: duplicated bus id "
1696                                 "(%d)\n", bus->mb_id);
1697                         return EINVAL;
1698                 }
1699         }
1700
1701         bus = NULL;
1702         if (strncmp(ent->bus_type, "PCI", 3) == 0) {
1703                 bus = kmalloc(sizeof(*bus), M_TEMP, M_WAITOK | M_ZERO);
1704                 bus->mb_type = MPTABLE_BUS_PCI;
1705         } else if (strncmp(ent->bus_type, "ISA", 3) == 0) {
1706                 bus = kmalloc(sizeof(*bus), M_TEMP, M_WAITOK | M_ZERO);
1707                 bus->mb_type = MPTABLE_BUS_ISA;
1708         }
1709
1710         if (bus != NULL) {
1711                 bus->mb_id = ent->bus_id;
1712                 TAILQ_INSERT_TAIL(&bus_info->mbi_list, bus, mb_link);
1713         }
1714         return 0;
1715 }
1716
1717 static void
1718 mptable_bus_info_alloc(const mpcth_t cth, struct mptable_bus_info *bus_info)
1719 {
1720         int error;
1721
1722         bzero(bus_info, sizeof(*bus_info));
1723         TAILQ_INIT(&bus_info->mbi_list);
1724
1725         error = mptable_iterate_entries(cth, mptable_bus_info_callback, bus_info);
1726         if (error)
1727                 mptable_bus_info_free(bus_info);
1728 }
1729
1730 static void
1731 mptable_bus_info_free(struct mptable_bus_info *bus_info)
1732 {
1733         struct mptable_bus *bus;
1734
1735         while ((bus = TAILQ_FIRST(&bus_info->mbi_list)) != NULL) {
1736                 TAILQ_REMOVE(&bus_info->mbi_list, bus, mb_link);
1737                 kfree(bus, M_TEMP);
1738         }
1739 }
1740
1741 struct mptable_lapic_cbarg1 {
1742         int     cpu_count;
1743         int     ht_fixup;
1744         u_int   ht_apicid_mask;
1745 };
1746
1747 static int
1748 mptable_lapic_pass1_callback(void *xarg, const void *pos, int type)
1749 {
1750         const struct PROCENTRY *ent;
1751         struct mptable_lapic_cbarg1 *arg = xarg;
1752
1753         if (type != 0)
1754                 return 0;
1755         ent = pos;
1756
1757         if ((ent->cpu_flags & PROCENTRY_FLAG_EN) == 0)
1758                 return 0;
1759
1760         arg->cpu_count++;
1761         if (ent->apic_id < 32) {
1762                 arg->ht_apicid_mask |= 1 << ent->apic_id;
1763         } else if (arg->ht_fixup) {
1764                 kprintf("MPTABLE: lapic id > 32, disable HTT fixup\n");
1765                 arg->ht_fixup = 0;
1766         }
1767         return 0;
1768 }
1769
1770 struct mptable_lapic_cbarg2 {
1771         int     cpu;
1772         int     logical_cpus;
1773         int     found_bsp;
1774 };
1775
1776 static int
1777 mptable_lapic_pass2_callback(void *xarg, const void *pos, int type)
1778 {
1779         const struct PROCENTRY *ent;
1780         struct mptable_lapic_cbarg2 *arg = xarg;
1781
1782         if (type != 0)
1783                 return 0;
1784         ent = pos;
1785
1786         if (ent->cpu_flags & PROCENTRY_FLAG_BP) {
1787                 KKASSERT(!arg->found_bsp);
1788                 arg->found_bsp = 1;
1789         }
1790
1791         if (processor_entry(ent, arg->cpu))
1792                 arg->cpu++;
1793
1794         if (arg->logical_cpus) {
1795                 struct PROCENTRY proc;
1796                 int i;
1797
1798                 /*
1799                  * Create fake mptable processor entries
1800                  * and feed them to processor_entry() to
1801                  * enumerate the logical CPUs.
1802                  */
1803                 bzero(&proc, sizeof(proc));
1804                 proc.type = 0;
1805                 proc.cpu_flags = PROCENTRY_FLAG_EN;
1806                 proc.apic_id = ent->apic_id;
1807
1808                 for (i = 1; i < arg->logical_cpus; i++) {
1809                         proc.apic_id++;
1810                         processor_entry(&proc, arg->cpu);
1811                         arg->cpu++;
1812                 }
1813         }
1814         return 0;
1815 }
1816
1817 static void
1818 mptable_lapic_default(void)
1819 {
1820         int ap_apicid, bsp_apicid;
1821
1822         mp_naps = 1; /* exclude BSP */
1823
1824         /* Map local apic before the id field is accessed */
1825         lapic_map(DEFAULT_APIC_BASE);
1826
1827         bsp_apicid = APIC_ID(lapic->id);
1828         ap_apicid = (bsp_apicid == 0) ? 1 : 0;
1829
1830         /* BSP */
1831         mp_set_cpuids(0, bsp_apicid);
1832         /* one and only AP */
1833         mp_set_cpuids(1, ap_apicid);
1834 }
1835
1836 /*
1837  * Configure:
1838  *     mp_naps
1839  *     ID_TO_CPU(N), APIC ID to logical CPU table
1840  *     CPU_TO_ID(N), logical CPU to APIC ID table
1841  */
1842 static void
1843 mptable_lapic_enumerate(struct lapic_enumerator *e)
1844 {
1845         struct mptable_pos mpt;
1846         struct mptable_lapic_cbarg1 arg1;
1847         struct mptable_lapic_cbarg2 arg2;
1848         mpcth_t cth;
1849         int error, logical_cpus = 0;
1850         vm_offset_t lapic_addr;
1851
1852         if (mptable_use_default) {
1853                 mptable_lapic_default();
1854                 return;
1855         }
1856  
1857         error = mptable_map(&mpt);
1858         if (error)
1859                 panic("mptable_lapic_enumerate mptable_map failed\n");
1860         KKASSERT(!MPTABLE_POS_USE_DEFAULT(&mpt));
1861
1862         cth = mpt.mp_cth;
1863  
1864         /* Save local apic address */
1865         lapic_addr = (vm_offset_t)cth->apic_address;
1866         KKASSERT(lapic_addr != 0);
1867  
1868         /*
1869          * Find out how many CPUs do we have
1870          */
1871         bzero(&arg1, sizeof(arg1));
1872         arg1.ht_fixup = 1; /* Apply ht fixup by default */
1873
1874         error = mptable_iterate_entries(cth,
1875                     mptable_lapic_pass1_callback, &arg1);
1876         if (error)
1877                 panic("mptable_iterate_entries(lapic_pass1) failed\n");
1878         KKASSERT(arg1.cpu_count != 0);
1879  
1880         /* See if we need to fixup HT logical CPUs. */
1881         if (arg1.ht_fixup) {
1882                 logical_cpus = mptable_hyperthread_fixup(arg1.ht_apicid_mask,
1883                                                          arg1.cpu_count);
1884                 if (logical_cpus != 0)
1885                         arg1.cpu_count *= logical_cpus;
1886         }
1887         mp_naps = arg1.cpu_count;
1888  
1889         /* Qualify the numbers again, after possible HT fixup */
1890         if (mp_naps > MAXCPU) {
1891                 kprintf("Warning: only using %d of %d available CPUs!\n",
1892                         MAXCPU, mp_naps);
1893                 DELAY(1000000);
1894                 mp_naps = MAXCPU;
1895         }
1896
1897         --mp_naps;      /* subtract the BSP */
1898
1899         /*
1900          * Link logical CPU id to local apic id
1901          */
1902         bzero(&arg2, sizeof(arg2));
1903         arg2.cpu = 1;
1904         arg2.logical_cpus = logical_cpus;
1905
1906         error = mptable_iterate_entries(cth,
1907                     mptable_lapic_pass2_callback, &arg2);
1908         if (error)
1909                 panic("mptable_iterate_entries(lapic_pass2) failed\n");
1910         KKASSERT(arg2.found_bsp);
1911
1912         /* Map local apic */
1913         lapic_map(lapic_addr);
1914
1915         mptable_unmap(&mpt);
1916 }
1917
1918 struct mptable_lapic_probe_cbarg {
1919         int     cpu_count;
1920         int     found_bsp;
1921 };
1922
1923 static int
1924 mptable_lapic_probe_callback(void *xarg, const void *pos, int type)
1925 {
1926         const struct PROCENTRY *ent;
1927         struct mptable_lapic_probe_cbarg *arg = xarg;
1928
1929         if (type != 0)
1930                 return 0;
1931         ent = pos;
1932
1933         if ((ent->cpu_flags & PROCENTRY_FLAG_EN) == 0)
1934                 return 0;
1935         arg->cpu_count++;
1936
1937         if (ent->cpu_flags & PROCENTRY_FLAG_BP) {
1938                 if (arg->found_bsp) {
1939                         kprintf("more than one BSP in base MP table\n");
1940                         return EINVAL;
1941                 }
1942                 arg->found_bsp = 1;
1943         }
1944         return 0;
1945 }
1946
1947 static int
1948 mptable_lapic_probe(struct lapic_enumerator *e)
1949 {
1950         struct mptable_pos mpt;
1951         struct mptable_lapic_probe_cbarg arg;
1952         mpcth_t cth;
1953         int error;
1954
1955         if (mptable_fps_phyaddr == 0)
1956                 return ENXIO;
1957
1958         if (mptable_use_default)
1959                 return 0;
1960
1961         error = mptable_map(&mpt);
1962         if (error)
1963                 return error;
1964         KKASSERT(!MPTABLE_POS_USE_DEFAULT(&mpt));
1965
1966         error = EINVAL;
1967         cth = mpt.mp_cth;
1968
1969         if (cth->apic_address == 0)
1970                 goto done;
1971
1972         bzero(&arg, sizeof(arg));
1973         error = mptable_iterate_entries(cth,
1974                     mptable_lapic_probe_callback, &arg);
1975         if (!error) {
1976                 if (arg.cpu_count == 0) {
1977                         kprintf("MP table contains no processor entries\n");
1978                         error = EINVAL;
1979                 } else if (!arg.found_bsp) {
1980                         kprintf("MP table does not contains BSP entry\n");
1981                         error = EINVAL;
1982                 }
1983         }
1984 done:
1985         mptable_unmap(&mpt);
1986         return error;
1987 }
1988
1989 static struct lapic_enumerator  mptable_lapic_enumerator = {
1990         .lapic_prio = LAPIC_ENUM_PRIO_MPTABLE,
1991         .lapic_probe = mptable_lapic_probe,
1992         .lapic_enumerate = mptable_lapic_enumerate
1993 };
1994
1995 static void
1996 mptable_lapic_enum_register(void)
1997 {
1998         lapic_enumerator_register(&mptable_lapic_enumerator);
1999 }
2000 SYSINIT(mptable_lapic, SI_BOOT2_PRESMP, SI_ORDER_ANY,
2001         mptable_lapic_enum_register, 0);
2002
2003 static int
2004 mptable_ioapic_list_callback(void *xarg, const void *pos, int type)
2005 {
2006         const struct IOAPICENTRY *ent;
2007         struct mptable_ioapic *nioapic, *ioapic;
2008
2009         if (type != 2)
2010                 return 0;
2011         ent = pos;
2012
2013         if ((ent->apic_flags & IOAPICENTRY_FLAG_EN) == 0)
2014                 return 0;
2015
2016         if (ent->apic_address == 0) {
2017                 kprintf("mptable_ioapic_create_list: zero IOAPIC addr\n");
2018                 return EINVAL;
2019         }
2020
2021         TAILQ_FOREACH(ioapic, &mptable_ioapic_list, mio_link) {
2022                 if (ioapic->mio_apic_id == ent->apic_id) {
2023                         kprintf("mptable_ioapic_create_list: duplicated "
2024                                 "apic id %d\n", ioapic->mio_apic_id);
2025                         return EINVAL;
2026                 }
2027                 if (ioapic->mio_addr == ent->apic_address) {
2028                         kprintf("mptable_ioapic_create_list: overlapped "
2029                                 "IOAPIC addr 0x%08x", ioapic->mio_addr);
2030                         return EINVAL;
2031                 }
2032         }
2033
2034         nioapic = kmalloc(sizeof(*nioapic), M_DEVBUF, M_WAITOK | M_ZERO);
2035         nioapic->mio_apic_id = ent->apic_id;
2036         nioapic->mio_addr = ent->apic_address;
2037
2038         /*
2039          * Create IOAPIC list in ascending order of APIC ID
2040          */
2041         TAILQ_FOREACH_REVERSE(ioapic, &mptable_ioapic_list,
2042             mptable_ioapic_list, mio_link) {
2043                 if (nioapic->mio_apic_id > ioapic->mio_apic_id) {
2044                         TAILQ_INSERT_AFTER(&mptable_ioapic_list,
2045                             ioapic, nioapic, mio_link);
2046                         break;
2047                 }
2048         }
2049         if (ioapic == NULL)
2050                 TAILQ_INSERT_HEAD(&mptable_ioapic_list, nioapic, mio_link);
2051
2052         return 0;
2053 }
2054
2055 static void
2056 mptable_ioapic_create_list(void)
2057 {
2058         struct mptable_ioapic *ioapic;
2059         struct mptable_pos mpt;
2060         int idx, error;
2061
2062         if (mptable_fps_phyaddr == 0)
2063                 return;
2064
2065         if (mptable_use_default) {
2066                 ioapic = kmalloc(sizeof(*ioapic), M_DEVBUF, M_WAITOK | M_ZERO);
2067                 ioapic->mio_idx = 0;
2068                 ioapic->mio_apic_id = 0;        /* NOTE: any value is ok here */
2069                 ioapic->mio_addr = 0xfec00000;  /* XXX magic number */
2070
2071                 TAILQ_INSERT_HEAD(&mptable_ioapic_list, ioapic, mio_link);
2072                 return;
2073         }
2074
2075         error = mptable_map(&mpt);
2076         if (error)
2077                 panic("mptable_ioapic_create_list: mptable_map failed\n");
2078         KKASSERT(!MPTABLE_POS_USE_DEFAULT(&mpt));
2079
2080         error = mptable_iterate_entries(mpt.mp_cth,
2081                     mptable_ioapic_list_callback, NULL);
2082         if (error) {
2083                 while ((ioapic = TAILQ_FIRST(&mptable_ioapic_list)) != NULL) {
2084                         TAILQ_REMOVE(&mptable_ioapic_list, ioapic, mio_link);
2085                         kfree(ioapic, M_DEVBUF);
2086                 }
2087                 goto done;
2088         }
2089
2090         /*
2091          * Assign index number for each IOAPIC
2092          */
2093         idx = 0;
2094         TAILQ_FOREACH(ioapic, &mptable_ioapic_list, mio_link) {
2095                 ioapic->mio_idx = idx;
2096                 ++idx;
2097         }
2098 done:
2099         mptable_unmap(&mpt);
2100 }
2101 SYSINIT(mptable_ioapic_list, SI_BOOT2_PRESMP, SI_ORDER_SECOND,
2102         mptable_ioapic_create_list, 0);
2103
2104 static int
2105 mptable_pci_int_callback(void *xarg, const void *pos, int type)
2106 {
2107         const struct mptable_bus_info *bus_info = xarg;
2108         const struct mptable_ioapic *ioapic;
2109         const struct mptable_bus *bus;
2110         struct mptable_pci_int *pci_int;
2111         const struct INTENTRY *ent;
2112         int pci_pin, pci_dev;
2113
2114         if (type != 3)
2115                 return 0;
2116         ent = pos;
2117
2118         if (ent->int_type != 0)
2119                 return 0;
2120
2121         TAILQ_FOREACH(bus, &bus_info->mbi_list, mb_link) {
2122                 if (bus->mb_type == MPTABLE_BUS_PCI &&
2123                     bus->mb_id == ent->src_bus_id)
2124                         break;
2125         }
2126         if (bus == NULL)
2127                 return 0;
2128
2129         TAILQ_FOREACH(ioapic, &mptable_ioapic_list, mio_link) {
2130                 if (ioapic->mio_apic_id == ent->dst_apic_id)
2131                         break;
2132         }
2133         if (ioapic == NULL) {
2134                 kprintf("MPTABLE: warning PCI int dst apic id %d "
2135                         "does not exist\n", ent->dst_apic_id);
2136                 return 0;
2137         }
2138
2139         pci_pin = ent->src_bus_irq & 0x3;
2140         pci_dev = (ent->src_bus_irq >> 2) & 0x1f;
2141
2142         TAILQ_FOREACH(pci_int, &mptable_pci_int_list, mpci_link) {
2143                 if (pci_int->mpci_bus == ent->src_bus_id &&
2144                     pci_int->mpci_dev == pci_dev &&
2145                     pci_int->mpci_pin == pci_pin) {
2146                         if (pci_int->mpci_ioapic_idx == ioapic->mio_idx &&
2147                             pci_int->mpci_ioapic_pin == ent->dst_apic_int) {
2148                                 kprintf("MPTABLE: warning duplicated "
2149                                         "PCI int entry for "
2150                                         "bus %d, dev %d, pin %d\n",
2151                                         pci_int->mpci_bus,
2152                                         pci_int->mpci_dev,
2153                                         pci_int->mpci_pin);
2154                                 return 0;
2155                         } else {
2156                                 kprintf("mptable_pci_int_register: "
2157                                         "conflict PCI int entry for "
2158                                         "bus %d, dev %d, pin %d, "
2159                                         "IOAPIC %d.%d -> %d.%d\n",
2160                                         pci_int->mpci_bus,
2161                                         pci_int->mpci_dev,
2162                                         pci_int->mpci_pin,
2163                                         pci_int->mpci_ioapic_idx,
2164                                         pci_int->mpci_ioapic_pin,
2165                                         ioapic->mio_idx,
2166                                         ent->dst_apic_int);
2167                                 return EINVAL;
2168                         }
2169                 }
2170         }
2171
2172         pci_int = kmalloc(sizeof(*pci_int), M_DEVBUF, M_WAITOK | M_ZERO);
2173
2174         pci_int->mpci_bus = ent->src_bus_id;
2175         pci_int->mpci_dev = pci_dev;
2176         pci_int->mpci_pin = pci_pin;
2177         pci_int->mpci_ioapic_idx = ioapic->mio_idx;
2178         pci_int->mpci_ioapic_pin = ent->dst_apic_int;
2179
2180         TAILQ_INSERT_TAIL(&mptable_pci_int_list, pci_int, mpci_link);
2181
2182         return 0;
2183 }
2184
2185 static void
2186 mptable_pci_int_register(void)
2187 {
2188         struct mptable_bus_info bus_info;
2189         const struct mptable_bus *bus;
2190         struct mptable_pci_int *pci_int;
2191         struct mptable_pos mpt;
2192         int error, force_pci0, npcibus;
2193         mpcth_t cth;
2194
2195         if (mptable_fps_phyaddr == 0)
2196                 return;
2197
2198         if (mptable_use_default)
2199                 return;
2200
2201         if (TAILQ_EMPTY(&mptable_ioapic_list))
2202                 return;
2203
2204         error = mptable_map(&mpt);
2205         if (error)
2206                 panic("mptable_pci_int_register: mptable_map failed\n");
2207         KKASSERT(!MPTABLE_POS_USE_DEFAULT(&mpt));
2208
2209         cth = mpt.mp_cth;
2210
2211         mptable_bus_info_alloc(cth, &bus_info);
2212         if (TAILQ_EMPTY(&bus_info.mbi_list))
2213                 goto done;
2214
2215         force_pci0 = 0;
2216         npcibus = 0;
2217         TAILQ_FOREACH(bus, &bus_info.mbi_list, mb_link) {
2218                 if (bus->mb_type == MPTABLE_BUS_PCI)
2219                         ++npcibus;
2220         }
2221         if (npcibus == 0) {
2222                 mptable_bus_info_free(&bus_info);
2223                 goto done;
2224         } else if (npcibus == 1) {
2225                 force_pci0 = 1;
2226         }
2227
2228         error = mptable_iterate_entries(cth,
2229                     mptable_pci_int_callback, &bus_info);
2230
2231         mptable_bus_info_free(&bus_info);
2232
2233         if (error) {
2234                 while ((pci_int = TAILQ_FIRST(&mptable_pci_int_list)) != NULL) {
2235                         TAILQ_REMOVE(&mptable_pci_int_list, pci_int, mpci_link);
2236                         kfree(pci_int, M_DEVBUF);
2237                 }
2238                 goto done;
2239         }
2240
2241         if (force_pci0) {
2242                 TAILQ_FOREACH(pci_int, &mptable_pci_int_list, mpci_link)
2243                         pci_int->mpci_bus = 0;
2244         }
2245 done:
2246         mptable_unmap(&mpt);
2247 }
2248 SYSINIT(mptable_pci, SI_BOOT2_PRESMP, SI_ORDER_ANY,
2249         mptable_pci_int_register, 0);
2250
2251 struct mptable_ioapic_probe_cbarg {
2252         const struct mptable_bus_info *bus_info;
2253 };
2254
2255 static int
2256 mptable_ioapic_probe_callback(void *xarg, const void *pos, int type)
2257 {
2258         struct mptable_ioapic_probe_cbarg *arg = xarg;
2259         const struct mptable_ioapic *ioapic;
2260         const struct mptable_bus *bus;
2261         const struct INTENTRY *ent;
2262
2263         if (type != 3)
2264                 return 0;
2265         ent = pos;
2266
2267         if (ent->int_type != 0)
2268                 return 0;
2269
2270         TAILQ_FOREACH(bus, &arg->bus_info->mbi_list, mb_link) {
2271                 if (bus->mb_type == MPTABLE_BUS_ISA &&
2272                     bus->mb_id == ent->src_bus_id)
2273                         break;
2274         }
2275         if (bus == NULL)
2276                 return 0;
2277
2278         TAILQ_FOREACH(ioapic, &mptable_ioapic_list, mio_link) {
2279                 if (ioapic->mio_apic_id == ent->dst_apic_id)
2280                         break;
2281         }
2282         if (ioapic == NULL) {
2283                 kprintf("MPTABLE: warning ISA int dst apic id %d "
2284                         "does not exist\n", ent->dst_apic_id);
2285                 return 0;
2286         }
2287
2288         /* XXX magic number */
2289         if (ent->src_bus_irq >= 16) {
2290                 kprintf("mptable_ioapic_probe: invalid ISA irq (%d)\n",
2291                         ent->src_bus_irq);
2292                 return EINVAL;
2293         }
2294         return 0;
2295 }
2296
2297 static int
2298 mptable_ioapic_probe(struct ioapic_enumerator *e)
2299 {
2300         struct mptable_ioapic_probe_cbarg arg;
2301         struct mptable_bus_info bus_info;
2302         struct mptable_pos mpt;
2303         mpcth_t cth;
2304         int error;
2305
2306         if (mptable_fps_phyaddr == 0)
2307                 return ENXIO;
2308
2309         if (mptable_use_default)
2310                 return 0;
2311
2312         if (TAILQ_EMPTY(&mptable_ioapic_list))
2313                 return ENXIO;
2314
2315         error = mptable_map(&mpt);
2316         if (error)
2317                 panic("mptable_ioapic_probe: mptable_map failed\n");
2318         KKASSERT(!MPTABLE_POS_USE_DEFAULT(&mpt));
2319
2320         cth = mpt.mp_cth;
2321
2322         mptable_bus_info_alloc(cth, &bus_info);
2323
2324         bzero(&arg, sizeof(arg));
2325         arg.bus_info = &bus_info;
2326
2327         error = mptable_iterate_entries(cth,
2328                     mptable_ioapic_probe_callback, &arg);
2329
2330         mptable_bus_info_free(&bus_info);
2331         mptable_unmap(&mpt);
2332
2333         return error;
2334 }
2335
2336 struct mptable_ioapic_int_cbarg {
2337         const struct mptable_bus_info *bus_info;
2338         int     ioapic_nint;
2339 };
2340
2341 static int
2342 mptable_ioapic_int_callback(void *xarg, const void *pos, int type)
2343 {
2344         struct mptable_ioapic_int_cbarg *arg = xarg;
2345         const struct mptable_ioapic *ioapic;
2346         const struct mptable_bus *bus;
2347         const struct INTENTRY *ent;
2348         int gsi;
2349
2350         if (type != 3)
2351                 return 0;
2352
2353         arg->ioapic_nint++;
2354
2355         ent = pos;
2356         if (ent->int_type != 0)
2357                 return 0;
2358
2359         TAILQ_FOREACH(bus, &arg->bus_info->mbi_list, mb_link) {
2360                 if (bus->mb_type == MPTABLE_BUS_ISA &&
2361                     bus->mb_id == ent->src_bus_id)
2362                         break;
2363         }
2364         if (bus == NULL)
2365                 return 0;
2366
2367         TAILQ_FOREACH(ioapic, &mptable_ioapic_list, mio_link) {
2368                 if (ioapic->mio_apic_id == ent->dst_apic_id)
2369                         break;
2370         }
2371         if (ioapic == NULL) {
2372                 kprintf("MPTABLE: warning ISA int dst apic id %d "
2373                         "does not exist\n", ent->dst_apic_id);
2374                 return 0;
2375         }
2376
2377         if (ent->dst_apic_int >= ioapic->mio_npin) {
2378                 panic("mptable_ioapic_enumerate: invalid I/O APIC "
2379                       "pin %d, should be < %d",
2380                       ent->dst_apic_int, ioapic->mio_npin);
2381         }
2382         gsi = ioapic->mio_gsi_base + ent->dst_apic_int;
2383
2384         if (ent->src_bus_irq != gsi) {
2385                 if (bootverbose) {
2386                         kprintf("MPTABLE: INTSRC irq %d -> GSI %d\n",
2387                                 ent->src_bus_irq, gsi);
2388                 }
2389                 ioapic_intsrc(ent->src_bus_irq, gsi,
2390                     INTR_TRIGGER_EDGE, INTR_POLARITY_HIGH);
2391         }
2392         return 0;
2393 }
2394
2395 static void
2396 mptable_ioapic_enumerate(struct ioapic_enumerator *e)
2397 {
2398         struct mptable_bus_info bus_info;
2399         struct mptable_ioapic *ioapic;
2400         struct mptable_pos mpt;
2401         mpcth_t cth;
2402         int error;
2403
2404         KKASSERT(mptable_fps_phyaddr != 0);
2405         KKASSERT(!TAILQ_EMPTY(&mptable_ioapic_list));
2406
2407         TAILQ_FOREACH(ioapic, &mptable_ioapic_list, mio_link) {
2408                 const struct mptable_ioapic *prev_ioapic;
2409                 uint32_t ver;
2410                 void *addr;
2411
2412                 addr = ioapic_map(ioapic->mio_addr);
2413
2414                 ver = ioapic_read(addr, IOAPIC_VER);
2415                 ioapic->mio_npin = ((ver & IOART_VER_MAXREDIR)
2416                                     >> MAXREDIRSHIFT) + 1;
2417
2418                 prev_ioapic = TAILQ_PREV(ioapic,
2419                                 mptable_ioapic_list, mio_link);
2420                 if (prev_ioapic == NULL) {
2421                         ioapic->mio_gsi_base = 0;
2422                 } else {
2423                         ioapic->mio_gsi_base =
2424                                 prev_ioapic->mio_gsi_base +
2425                                 prev_ioapic->mio_npin;
2426                 }
2427                 ioapic_add(addr, ioapic->mio_gsi_base, ioapic->mio_npin);
2428
2429                 if (bootverbose) {
2430                         kprintf("MPTABLE: IOAPIC addr 0x%08x, "
2431                                 "apic id %d, idx %d, gsi base %d, npin %d\n",
2432                                 ioapic->mio_addr,
2433                                 ioapic->mio_apic_id,
2434                                 ioapic->mio_idx,
2435                                 ioapic->mio_gsi_base,
2436                                 ioapic->mio_npin);
2437                 }
2438         }
2439
2440         if (mptable_use_default) {
2441                 if (bootverbose)
2442                         kprintf("MPTABLE: INTSRC irq 0 -> GSI 2 (default)\n");
2443                 ioapic_intsrc(0, 2, INTR_TRIGGER_EDGE, INTR_POLARITY_HIGH);
2444                 return;
2445         }
2446
2447         error = mptable_map(&mpt);
2448         if (error)
2449                 panic("mptable_ioapic_probe: mptable_map failed\n");
2450         KKASSERT(!MPTABLE_POS_USE_DEFAULT(&mpt));
2451
2452         cth = mpt.mp_cth;
2453
2454         mptable_bus_info_alloc(cth, &bus_info);
2455
2456         if (TAILQ_EMPTY(&bus_info.mbi_list)) {
2457                 if (bootverbose)
2458                         kprintf("MPTABLE: INTSRC irq 0 -> GSI 2 (no bus)\n");
2459                 ioapic_intsrc(0, 2, INTR_TRIGGER_EDGE, INTR_POLARITY_HIGH);
2460         } else {
2461                 struct mptable_ioapic_int_cbarg arg;
2462
2463                 bzero(&arg, sizeof(arg));
2464                 arg.bus_info = &bus_info;
2465
2466                 error = mptable_iterate_entries(cth,
2467                             mptable_ioapic_int_callback, &arg);
2468                 if (error)
2469                         panic("mptable_ioapic_int failed\n");
2470
2471                 if (arg.ioapic_nint == 0) {
2472                         if (bootverbose) {
2473                                 kprintf("MPTABLE: INTSRC irq 0 -> GSI 2 "
2474                                         "(no int)\n");
2475                         }
2476                         ioapic_intsrc(0, 2, INTR_TRIGGER_EDGE,
2477                             INTR_POLARITY_HIGH);
2478                 }
2479         }
2480
2481         mptable_bus_info_free(&bus_info);
2482
2483         mptable_unmap(&mpt);
2484 }
2485
2486 static struct ioapic_enumerator mptable_ioapic_enumerator = {
2487         .ioapic_prio = IOAPIC_ENUM_PRIO_MPTABLE,
2488         .ioapic_probe = mptable_ioapic_probe,
2489         .ioapic_enumerate = mptable_ioapic_enumerate
2490 };
2491
2492 static void
2493 mptable_ioapic_enum_register(void)
2494 {
2495         ioapic_enumerator_register(&mptable_ioapic_enumerator);
2496 }
2497 SYSINIT(mptable_ioapic, SI_BOOT2_PRESMP, SI_ORDER_ANY,
2498         mptable_ioapic_enum_register, 0);
2499
2500 void
2501 mptable_pci_int_dump(void)
2502 {
2503         const struct mptable_pci_int *pci_int;
2504
2505         TAILQ_FOREACH(pci_int, &mptable_pci_int_list, mpci_link) {
2506                 kprintf("MPTABLE: %d:%d INT%c -> IOAPIC %d.%d\n",
2507                         pci_int->mpci_bus,
2508                         pci_int->mpci_dev,
2509                         pci_int->mpci_pin + 'A',
2510                         pci_int->mpci_ioapic_idx,
2511                         pci_int->mpci_ioapic_pin);
2512         }
2513 }
2514
2515 int
2516 mptable_pci_int_route(int bus, int dev, int pin, int intline)
2517 {
2518         const struct mptable_pci_int *pci_int;
2519         int irq = -1;
2520
2521         KKASSERT(pin >= 1);
2522         --pin;  /* zero based */
2523
2524         TAILQ_FOREACH(pci_int, &mptable_pci_int_list, mpci_link) {
2525                 if (pci_int->mpci_bus == bus &&
2526                     pci_int->mpci_dev == dev &&
2527                     pci_int->mpci_pin == pin)
2528                         break;
2529         }
2530         if (pci_int != NULL) {
2531                 int gsi;
2532
2533                 gsi = ioapic_gsi(pci_int->mpci_ioapic_idx,
2534                         pci_int->mpci_ioapic_pin);
2535                 if (gsi >= 0) {
2536                         irq = ioapic_abi_find_gsi(gsi,
2537                                 INTR_TRIGGER_LEVEL, INTR_POLARITY_LOW);
2538                 }
2539         }
2540
2541         if (irq < 0) {
2542                 if (bootverbose) {
2543                         kprintf("MPTABLE: fixed interrupt routing "
2544                                 "for %d:%d INT%c\n", bus, dev, pin + 'A');
2545                 }
2546
2547                 irq = ioapic_abi_find_irq(intline,
2548                         INTR_TRIGGER_LEVEL, INTR_POLARITY_LOW);
2549         }
2550
2551         if (irq >= 0 && bootverbose) {
2552                 kprintf("MPTABLE: %d:%d INT%c routed to irq %d\n",
2553                         bus, dev, pin + 'A', irq);
2554         }
2555         return irq;
2556 }