diff options
Diffstat (limited to 'arch/x86/kernel/apic_64.c')
-rw-r--r-- | arch/x86/kernel/apic_64.c | 1259 |
1 files changed, 643 insertions, 616 deletions
diff --git a/arch/x86/kernel/apic_64.c b/arch/x86/kernel/apic_64.c index f28ccb588fba..d8d03e09dea2 100644 --- a/arch/x86/kernel/apic_64.c +++ b/arch/x86/kernel/apic_64.c | |||
@@ -23,32 +23,37 @@ | |||
23 | #include <linux/mc146818rtc.h> | 23 | #include <linux/mc146818rtc.h> |
24 | #include <linux/kernel_stat.h> | 24 | #include <linux/kernel_stat.h> |
25 | #include <linux/sysdev.h> | 25 | #include <linux/sysdev.h> |
26 | #include <linux/module.h> | ||
27 | #include <linux/ioport.h> | 26 | #include <linux/ioport.h> |
28 | #include <linux/clockchips.h> | 27 | #include <linux/clockchips.h> |
28 | #include <linux/acpi_pmtmr.h> | ||
29 | #include <linux/module.h> | ||
29 | 30 | ||
30 | #include <asm/atomic.h> | 31 | #include <asm/atomic.h> |
31 | #include <asm/smp.h> | 32 | #include <asm/smp.h> |
32 | #include <asm/mtrr.h> | 33 | #include <asm/mtrr.h> |
33 | #include <asm/mpspec.h> | 34 | #include <asm/mpspec.h> |
35 | #include <asm/hpet.h> | ||
34 | #include <asm/pgalloc.h> | 36 | #include <asm/pgalloc.h> |
35 | #include <asm/mach_apic.h> | 37 | #include <asm/mach_apic.h> |
36 | #include <asm/nmi.h> | 38 | #include <asm/nmi.h> |
37 | #include <asm/idle.h> | 39 | #include <asm/idle.h> |
38 | #include <asm/proto.h> | 40 | #include <asm/proto.h> |
39 | #include <asm/timex.h> | 41 | #include <asm/timex.h> |
40 | #include <asm/hpet.h> | ||
41 | #include <asm/apic.h> | 42 | #include <asm/apic.h> |
42 | 43 | ||
43 | int apic_verbosity; | ||
44 | int disable_apic_timer __cpuinitdata; | 44 | int disable_apic_timer __cpuinitdata; |
45 | static int apic_calibrate_pmtmr __initdata; | 45 | static int apic_calibrate_pmtmr __initdata; |
46 | int disable_apic; | ||
46 | 47 | ||
47 | /* Local APIC timer works in C2? */ | 48 | /* Local APIC timer works in C2 */ |
48 | int local_apic_timer_c2_ok; | 49 | int local_apic_timer_c2_ok; |
49 | EXPORT_SYMBOL_GPL(local_apic_timer_c2_ok); | 50 | EXPORT_SYMBOL_GPL(local_apic_timer_c2_ok); |
50 | 51 | ||
51 | static struct resource *ioapic_resources; | 52 | /* |
53 | * Debug level, exported for io_apic.c | ||
54 | */ | ||
55 | int apic_verbosity; | ||
56 | |||
52 | static struct resource lapic_resource = { | 57 | static struct resource lapic_resource = { |
53 | .name = "Local APIC", | 58 | .name = "Local APIC", |
54 | .flags = IORESOURCE_MEM | IORESOURCE_BUSY, | 59 | .flags = IORESOURCE_MEM | IORESOURCE_BUSY, |
@@ -60,10 +65,8 @@ static int lapic_next_event(unsigned long delta, | |||
60 | struct clock_event_device *evt); | 65 | struct clock_event_device *evt); |
61 | static void lapic_timer_setup(enum clock_event_mode mode, | 66 | static void lapic_timer_setup(enum clock_event_mode mode, |
62 | struct clock_event_device *evt); | 67 | struct clock_event_device *evt); |
63 | |||
64 | static void lapic_timer_broadcast(cpumask_t mask); | 68 | static void lapic_timer_broadcast(cpumask_t mask); |
65 | 69 | static void apic_pm_activate(void); | |
66 | static void __setup_APIC_LVTT(unsigned int clocks, int oneshot, int irqen); | ||
67 | 70 | ||
68 | static struct clock_event_device lapic_clockevent = { | 71 | static struct clock_event_device lapic_clockevent = { |
69 | .name = "lapic", | 72 | .name = "lapic", |
@@ -78,6 +81,150 @@ static struct clock_event_device lapic_clockevent = { | |||
78 | }; | 81 | }; |
79 | static DEFINE_PER_CPU(struct clock_event_device, lapic_events); | 82 | static DEFINE_PER_CPU(struct clock_event_device, lapic_events); |
80 | 83 | ||
84 | static unsigned long apic_phys; | ||
85 | |||
86 | /* | ||
87 | * Get the LAPIC version | ||
88 | */ | ||
89 | static inline int lapic_get_version(void) | ||
90 | { | ||
91 | return GET_APIC_VERSION(apic_read(APIC_LVR)); | ||
92 | } | ||
93 | |||
94 | /* | ||
95 | * Check, if the APIC is integrated or a seperate chip | ||
96 | */ | ||
97 | static inline int lapic_is_integrated(void) | ||
98 | { | ||
99 | return 1; | ||
100 | } | ||
101 | |||
102 | /* | ||
103 | * Check, whether this is a modern or a first generation APIC | ||
104 | */ | ||
105 | static int modern_apic(void) | ||
106 | { | ||
107 | /* AMD systems use old APIC versions, so check the CPU */ | ||
108 | if (boot_cpu_data.x86_vendor == X86_VENDOR_AMD && | ||
109 | boot_cpu_data.x86 >= 0xf) | ||
110 | return 1; | ||
111 | return lapic_get_version() >= 0x14; | ||
112 | } | ||
113 | |||
114 | void apic_wait_icr_idle(void) | ||
115 | { | ||
116 | while (apic_read(APIC_ICR) & APIC_ICR_BUSY) | ||
117 | cpu_relax(); | ||
118 | } | ||
119 | |||
120 | u32 safe_apic_wait_icr_idle(void) | ||
121 | { | ||
122 | u32 send_status; | ||
123 | int timeout; | ||
124 | |||
125 | timeout = 0; | ||
126 | do { | ||
127 | send_status = apic_read(APIC_ICR) & APIC_ICR_BUSY; | ||
128 | if (!send_status) | ||
129 | break; | ||
130 | udelay(100); | ||
131 | } while (timeout++ < 1000); | ||
132 | |||
133 | return send_status; | ||
134 | } | ||
135 | |||
136 | /** | ||
137 | * enable_NMI_through_LVT0 - enable NMI through local vector table 0 | ||
138 | */ | ||
139 | void __cpuinit enable_NMI_through_LVT0(void) | ||
140 | { | ||
141 | unsigned int v; | ||
142 | |||
143 | /* unmask and set to NMI */ | ||
144 | v = APIC_DM_NMI; | ||
145 | apic_write(APIC_LVT0, v); | ||
146 | } | ||
147 | |||
148 | /** | ||
149 | * lapic_get_maxlvt - get the maximum number of local vector table entries | ||
150 | */ | ||
151 | int lapic_get_maxlvt(void) | ||
152 | { | ||
153 | unsigned int v, maxlvt; | ||
154 | |||
155 | v = apic_read(APIC_LVR); | ||
156 | maxlvt = GET_APIC_MAXLVT(v); | ||
157 | return maxlvt; | ||
158 | } | ||
159 | |||
160 | /* | ||
161 | * This function sets up the local APIC timer, with a timeout of | ||
162 | * 'clocks' APIC bus clock. During calibration we actually call | ||
163 | * this function twice on the boot CPU, once with a bogus timeout | ||
164 | * value, second time for real. The other (noncalibrating) CPUs | ||
165 | * call this function only once, with the real, calibrated value. | ||
166 | * | ||
167 | * We do reads before writes even if unnecessary, to get around the | ||
168 | * P5 APIC double write bug. | ||
169 | */ | ||
170 | |||
171 | static void __setup_APIC_LVTT(unsigned int clocks, int oneshot, int irqen) | ||
172 | { | ||
173 | unsigned int lvtt_value, tmp_value; | ||
174 | |||
175 | lvtt_value = LOCAL_TIMER_VECTOR; | ||
176 | if (!oneshot) | ||
177 | lvtt_value |= APIC_LVT_TIMER_PERIODIC; | ||
178 | if (!irqen) | ||
179 | lvtt_value |= APIC_LVT_MASKED; | ||
180 | |||
181 | apic_write(APIC_LVTT, lvtt_value); | ||
182 | |||
183 | /* | ||
184 | * Divide PICLK by 16 | ||
185 | */ | ||
186 | tmp_value = apic_read(APIC_TDCR); | ||
187 | apic_write(APIC_TDCR, (tmp_value | ||
188 | & ~(APIC_TDR_DIV_1 | APIC_TDR_DIV_TMBASE)) | ||
189 | | APIC_TDR_DIV_16); | ||
190 | |||
191 | if (!oneshot) | ||
192 | apic_write(APIC_TMICT, clocks); | ||
193 | } | ||
194 | |||
195 | /* | ||
196 | * Setup extended LVT, AMD specific (K8, family 10h) | ||
197 | * | ||
198 | * Vector mappings are hard coded. On K8 only offset 0 (APIC500) and | ||
199 | * MCE interrupts are supported. Thus MCE offset must be set to 0. | ||
200 | */ | ||
201 | |||
202 | #define APIC_EILVT_LVTOFF_MCE 0 | ||
203 | #define APIC_EILVT_LVTOFF_IBS 1 | ||
204 | |||
205 | static void setup_APIC_eilvt(u8 lvt_off, u8 vector, u8 msg_type, u8 mask) | ||
206 | { | ||
207 | unsigned long reg = (lvt_off << 4) + APIC_EILVT0; | ||
208 | unsigned int v = (mask << 16) | (msg_type << 8) | vector; | ||
209 | |||
210 | apic_write(reg, v); | ||
211 | } | ||
212 | |||
213 | u8 setup_APIC_eilvt_mce(u8 vector, u8 msg_type, u8 mask) | ||
214 | { | ||
215 | setup_APIC_eilvt(APIC_EILVT_LVTOFF_MCE, vector, msg_type, mask); | ||
216 | return APIC_EILVT_LVTOFF_MCE; | ||
217 | } | ||
218 | |||
219 | u8 setup_APIC_eilvt_ibs(u8 vector, u8 msg_type, u8 mask) | ||
220 | { | ||
221 | setup_APIC_eilvt(APIC_EILVT_LVTOFF_IBS, vector, msg_type, mask); | ||
222 | return APIC_EILVT_LVTOFF_IBS; | ||
223 | } | ||
224 | |||
225 | /* | ||
226 | * Program the next event, relative to now | ||
227 | */ | ||
81 | static int lapic_next_event(unsigned long delta, | 228 | static int lapic_next_event(unsigned long delta, |
82 | struct clock_event_device *evt) | 229 | struct clock_event_device *evt) |
83 | { | 230 | { |
@@ -85,6 +232,9 @@ static int lapic_next_event(unsigned long delta, | |||
85 | return 0; | 232 | return 0; |
86 | } | 233 | } |
87 | 234 | ||
235 | /* | ||
236 | * Setup the lapic timer in periodic or oneshot mode | ||
237 | */ | ||
88 | static void lapic_timer_setup(enum clock_event_mode mode, | 238 | static void lapic_timer_setup(enum clock_event_mode mode, |
89 | struct clock_event_device *evt) | 239 | struct clock_event_device *evt) |
90 | { | 240 | { |
@@ -127,75 +277,261 @@ static void lapic_timer_broadcast(cpumask_t mask) | |||
127 | #endif | 277 | #endif |
128 | } | 278 | } |
129 | 279 | ||
130 | static void apic_pm_activate(void); | 280 | /* |
281 | * Setup the local APIC timer for this CPU. Copy the initilized values | ||
282 | * of the boot CPU and register the clock event in the framework. | ||
283 | */ | ||
284 | static void setup_APIC_timer(void) | ||
285 | { | ||
286 | struct clock_event_device *levt = &__get_cpu_var(lapic_events); | ||
131 | 287 | ||
132 | void apic_wait_icr_idle(void) | 288 | memcpy(levt, &lapic_clockevent, sizeof(*levt)); |
289 | levt->cpumask = cpumask_of_cpu(smp_processor_id()); | ||
290 | |||
291 | clockevents_register_device(levt); | ||
292 | } | ||
293 | |||
294 | /* | ||
295 | * In this function we calibrate APIC bus clocks to the external | ||
296 | * timer. Unfortunately we cannot use jiffies and the timer irq | ||
297 | * to calibrate, since some later bootup code depends on getting | ||
298 | * the first irq? Ugh. | ||
299 | * | ||
300 | * We want to do the calibration only once since we | ||
301 | * want to have local timer irqs syncron. CPUs connected | ||
302 | * by the same APIC bus have the very same bus frequency. | ||
303 | * And we want to have irqs off anyways, no accidental | ||
304 | * APIC irq that way. | ||
305 | */ | ||
306 | |||
307 | #define TICK_COUNT 100000000 | ||
308 | |||
309 | static void __init calibrate_APIC_clock(void) | ||
133 | { | 310 | { |
134 | while (apic_read(APIC_ICR) & APIC_ICR_BUSY) | 311 | unsigned apic, apic_start; |
135 | cpu_relax(); | 312 | unsigned long tsc, tsc_start; |
313 | int result; | ||
314 | |||
315 | local_irq_disable(); | ||
316 | |||
317 | /* | ||
318 | * Put whatever arbitrary (but long enough) timeout | ||
319 | * value into the APIC clock, we just want to get the | ||
320 | * counter running for calibration. | ||
321 | * | ||
322 | * No interrupt enable ! | ||
323 | */ | ||
324 | __setup_APIC_LVTT(250000000, 0, 0); | ||
325 | |||
326 | apic_start = apic_read(APIC_TMCCT); | ||
327 | #ifdef CONFIG_X86_PM_TIMER | ||
328 | if (apic_calibrate_pmtmr && pmtmr_ioport) { | ||
329 | pmtimer_wait(5000); /* 5ms wait */ | ||
330 | apic = apic_read(APIC_TMCCT); | ||
331 | result = (apic_start - apic) * 1000L / 5; | ||
332 | } else | ||
333 | #endif | ||
334 | { | ||
335 | rdtscll(tsc_start); | ||
336 | |||
337 | do { | ||
338 | apic = apic_read(APIC_TMCCT); | ||
339 | rdtscll(tsc); | ||
340 | } while ((tsc - tsc_start) < TICK_COUNT && | ||
341 | (apic_start - apic) < TICK_COUNT); | ||
342 | |||
343 | result = (apic_start - apic) * 1000L * tsc_khz / | ||
344 | (tsc - tsc_start); | ||
345 | } | ||
346 | |||
347 | local_irq_enable(); | ||
348 | |||
349 | printk(KERN_DEBUG "APIC timer calibration result %d\n", result); | ||
350 | |||
351 | printk(KERN_INFO "Detected %d.%03d MHz APIC timer.\n", | ||
352 | result / 1000 / 1000, result / 1000 % 1000); | ||
353 | |||
354 | /* Calculate the scaled math multiplication factor */ | ||
355 | lapic_clockevent.mult = div_sc(result, NSEC_PER_SEC, 32); | ||
356 | lapic_clockevent.max_delta_ns = | ||
357 | clockevent_delta2ns(0x7FFFFF, &lapic_clockevent); | ||
358 | lapic_clockevent.min_delta_ns = | ||
359 | clockevent_delta2ns(0xF, &lapic_clockevent); | ||
360 | |||
361 | calibration_result = result / HZ; | ||
136 | } | 362 | } |
137 | 363 | ||
138 | unsigned int safe_apic_wait_icr_idle(void) | 364 | /* |
365 | * Setup the boot APIC | ||
366 | * | ||
367 | * Calibrate and verify the result. | ||
368 | */ | ||
369 | void __init setup_boot_APIC_clock(void) | ||
139 | { | 370 | { |
140 | unsigned int send_status; | 371 | /* |
141 | int timeout; | 372 | * The local apic timer can be disabled via the kernel commandline. |
373 | * Register the lapic timer as a dummy clock event source on SMP | ||
374 | * systems, so the broadcast mechanism is used. On UP systems simply | ||
375 | * ignore it. | ||
376 | */ | ||
377 | if (disable_apic_timer) { | ||
378 | printk(KERN_INFO "Disabling APIC timer\n"); | ||
379 | /* No broadcast on UP ! */ | ||
380 | if (num_possible_cpus() > 1) { | ||
381 | lapic_clockevent.mult = 1; | ||
382 | setup_APIC_timer(); | ||
383 | } | ||
384 | return; | ||
385 | } | ||
142 | 386 | ||
143 | timeout = 0; | 387 | printk(KERN_INFO "Using local APIC timer interrupts.\n"); |
144 | do { | 388 | calibrate_APIC_clock(); |
145 | send_status = apic_read(APIC_ICR) & APIC_ICR_BUSY; | ||
146 | if (!send_status) | ||
147 | break; | ||
148 | udelay(100); | ||
149 | } while (timeout++ < 1000); | ||
150 | 389 | ||
151 | return send_status; | 390 | /* |
391 | * Do a sanity check on the APIC calibration result | ||
392 | */ | ||
393 | if (calibration_result < (1000000 / HZ)) { | ||
394 | printk(KERN_WARNING | ||
395 | "APIC frequency too slow, disabling apic timer\n"); | ||
396 | /* No broadcast on UP ! */ | ||
397 | if (num_possible_cpus() > 1) | ||
398 | setup_APIC_timer(); | ||
399 | return; | ||
400 | } | ||
401 | |||
402 | /* | ||
403 | * If nmi_watchdog is set to IO_APIC, we need the | ||
404 | * PIT/HPET going. Otherwise register lapic as a dummy | ||
405 | * device. | ||
406 | */ | ||
407 | if (nmi_watchdog != NMI_IO_APIC) | ||
408 | lapic_clockevent.features &= ~CLOCK_EVT_FEAT_DUMMY; | ||
409 | else | ||
410 | printk(KERN_WARNING "APIC timer registered as dummy," | ||
411 | " due to nmi_watchdog=1!\n"); | ||
412 | |||
413 | setup_APIC_timer(); | ||
152 | } | 414 | } |
153 | 415 | ||
154 | void enable_NMI_through_LVT0 (void * dummy) | 416 | /* |
417 | * AMD C1E enabled CPUs have a real nasty problem: Some BIOSes set the | ||
418 | * C1E flag only in the secondary CPU, so when we detect the wreckage | ||
419 | * we already have enabled the boot CPU local apic timer. Check, if | ||
420 | * disable_apic_timer is set and the DUMMY flag is cleared. If yes, | ||
421 | * set the DUMMY flag again and force the broadcast mode in the | ||
422 | * clockevents layer. | ||
423 | */ | ||
424 | void __cpuinit check_boot_apic_timer_broadcast(void) | ||
155 | { | 425 | { |
156 | unsigned int v; | 426 | if (!disable_apic_timer || |
427 | (lapic_clockevent.features & CLOCK_EVT_FEAT_DUMMY)) | ||
428 | return; | ||
157 | 429 | ||
158 | /* unmask and set to NMI */ | 430 | printk(KERN_INFO "AMD C1E detected late. Force timer broadcast.\n"); |
159 | v = APIC_DM_NMI; | 431 | lapic_clockevent.features |= CLOCK_EVT_FEAT_DUMMY; |
160 | apic_write(APIC_LVT0, v); | 432 | |
433 | local_irq_enable(); | ||
434 | clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_FORCE, &boot_cpu_id); | ||
435 | local_irq_disable(); | ||
161 | } | 436 | } |
162 | 437 | ||
163 | int get_maxlvt(void) | 438 | void __cpuinit setup_secondary_APIC_clock(void) |
164 | { | 439 | { |
165 | unsigned int v, maxlvt; | 440 | check_boot_apic_timer_broadcast(); |
441 | setup_APIC_timer(); | ||
442 | } | ||
166 | 443 | ||
167 | v = apic_read(APIC_LVR); | 444 | /* |
168 | maxlvt = GET_APIC_MAXLVT(v); | 445 | * The guts of the apic timer interrupt |
169 | return maxlvt; | 446 | */ |
447 | static void local_apic_timer_interrupt(void) | ||
448 | { | ||
449 | int cpu = smp_processor_id(); | ||
450 | struct clock_event_device *evt = &per_cpu(lapic_events, cpu); | ||
451 | |||
452 | /* | ||
453 | * Normally we should not be here till LAPIC has been initialized but | ||
454 | * in some cases like kdump, its possible that there is a pending LAPIC | ||
455 | * timer interrupt from previous kernel's context and is delivered in | ||
456 | * new kernel the moment interrupts are enabled. | ||
457 | * | ||
458 | * Interrupts are enabled early and LAPIC is setup much later, hence | ||
459 | * its possible that when we get here evt->event_handler is NULL. | ||
460 | * Check for event_handler being NULL and discard the interrupt as | ||
461 | * spurious. | ||
462 | */ | ||
463 | if (!evt->event_handler) { | ||
464 | printk(KERN_WARNING | ||
465 | "Spurious LAPIC timer interrupt on cpu %d\n", cpu); | ||
466 | /* Switch it off */ | ||
467 | lapic_timer_setup(CLOCK_EVT_MODE_SHUTDOWN, evt); | ||
468 | return; | ||
469 | } | ||
470 | |||
471 | /* | ||
472 | * the NMI deadlock-detector uses this. | ||
473 | */ | ||
474 | add_pda(apic_timer_irqs, 1); | ||
475 | |||
476 | evt->event_handler(evt); | ||
170 | } | 477 | } |
171 | 478 | ||
172 | /* | 479 | /* |
173 | * 'what should we do if we get a hw irq event on an illegal vector'. | 480 | * Local APIC timer interrupt. This is the most natural way for doing |
174 | * each architecture has to answer this themselves. | 481 | * local interrupts, but local timer interrupts can be emulated by |
482 | * broadcast interrupts too. [in case the hw doesn't support APIC timers] | ||
483 | * | ||
484 | * [ if a single-CPU system runs an SMP kernel then we call the local | ||
485 | * interrupt as well. Thus we cannot inline the local irq ... ] | ||
175 | */ | 486 | */ |
176 | void ack_bad_irq(unsigned int irq) | 487 | void smp_apic_timer_interrupt(struct pt_regs *regs) |
177 | { | 488 | { |
178 | printk("unexpected IRQ trap at vector %02x\n", irq); | 489 | struct pt_regs *old_regs = set_irq_regs(regs); |
490 | |||
179 | /* | 491 | /* |
180 | * Currently unexpected vectors happen only on SMP and APIC. | 492 | * NOTE! We'd better ACK the irq immediately, |
181 | * We _must_ ack these because every local APIC has only N | 493 | * because timer handling can be slow. |
182 | * irq slots per priority level, and a 'hanging, unacked' IRQ | ||
183 | * holds up an irq slot - in excessive cases (when multiple | ||
184 | * unexpected vectors occur) that might lock up the APIC | ||
185 | * completely. | ||
186 | * But don't ack when the APIC is disabled. -AK | ||
187 | */ | 494 | */ |
188 | if (!disable_apic) | 495 | ack_APIC_irq(); |
189 | ack_APIC_irq(); | 496 | /* |
497 | * update_process_times() expects us to have done irq_enter(). | ||
498 | * Besides, if we don't timer interrupts ignore the global | ||
499 | * interrupt lock, which is the WrongThing (tm) to do. | ||
500 | */ | ||
501 | exit_idle(); | ||
502 | irq_enter(); | ||
503 | local_apic_timer_interrupt(); | ||
504 | irq_exit(); | ||
505 | set_irq_regs(old_regs); | ||
506 | } | ||
507 | |||
508 | int setup_profiling_timer(unsigned int multiplier) | ||
509 | { | ||
510 | return -EINVAL; | ||
190 | } | 511 | } |
191 | 512 | ||
513 | |||
514 | /* | ||
515 | * Local APIC start and shutdown | ||
516 | */ | ||
517 | |||
518 | /** | ||
519 | * clear_local_APIC - shutdown the local APIC | ||
520 | * | ||
521 | * This is called, when a CPU is disabled and before rebooting, so the state of | ||
522 | * the local APIC has no dangling leftovers. Also used to cleanout any BIOS | ||
523 | * leftovers during boot. | ||
524 | */ | ||
192 | void clear_local_APIC(void) | 525 | void clear_local_APIC(void) |
193 | { | 526 | { |
194 | int maxlvt; | 527 | int maxlvt = lapic_get_maxlvt(); |
195 | unsigned int v; | 528 | u32 v; |
196 | 529 | ||
197 | maxlvt = get_maxlvt(); | 530 | /* APIC hasn't been mapped yet */ |
531 | if (!apic_phys) | ||
532 | return; | ||
198 | 533 | ||
534 | maxlvt = lapic_get_maxlvt(); | ||
199 | /* | 535 | /* |
200 | * Masking an LVT entry can trigger a local APIC error | 536 | * Masking an LVT entry can trigger a local APIC error |
201 | * if the vector is zero. Mask LVTERR first to prevent this. | 537 | * if the vector is zero. Mask LVTERR first to prevent this. |
@@ -233,45 +569,9 @@ void clear_local_APIC(void) | |||
233 | apic_read(APIC_ESR); | 569 | apic_read(APIC_ESR); |
234 | } | 570 | } |
235 | 571 | ||
236 | void disconnect_bsp_APIC(int virt_wire_setup) | 572 | /** |
237 | { | 573 | * disable_local_APIC - clear and disable the local APIC |
238 | /* Go back to Virtual Wire compatibility mode */ | 574 | */ |
239 | unsigned long value; | ||
240 | |||
241 | /* For the spurious interrupt use vector F, and enable it */ | ||
242 | value = apic_read(APIC_SPIV); | ||
243 | value &= ~APIC_VECTOR_MASK; | ||
244 | value |= APIC_SPIV_APIC_ENABLED; | ||
245 | value |= 0xf; | ||
246 | apic_write(APIC_SPIV, value); | ||
247 | |||
248 | if (!virt_wire_setup) { | ||
249 | /* | ||
250 | * For LVT0 make it edge triggered, active high, | ||
251 | * external and enabled | ||
252 | */ | ||
253 | value = apic_read(APIC_LVT0); | ||
254 | value &= ~(APIC_MODE_MASK | APIC_SEND_PENDING | | ||
255 | APIC_INPUT_POLARITY | APIC_LVT_REMOTE_IRR | | ||
256 | APIC_LVT_LEVEL_TRIGGER | APIC_LVT_MASKED ); | ||
257 | value |= APIC_LVT_REMOTE_IRR | APIC_SEND_PENDING; | ||
258 | value = SET_APIC_DELIVERY_MODE(value, APIC_MODE_EXTINT); | ||
259 | apic_write(APIC_LVT0, value); | ||
260 | } else { | ||
261 | /* Disable LVT0 */ | ||
262 | apic_write(APIC_LVT0, APIC_LVT_MASKED); | ||
263 | } | ||
264 | |||
265 | /* For LVT1 make it edge triggered, active high, nmi and enabled */ | ||
266 | value = apic_read(APIC_LVT1); | ||
267 | value &= ~(APIC_MODE_MASK | APIC_SEND_PENDING | | ||
268 | APIC_INPUT_POLARITY | APIC_LVT_REMOTE_IRR | | ||
269 | APIC_LVT_LEVEL_TRIGGER | APIC_LVT_MASKED); | ||
270 | value |= APIC_LVT_REMOTE_IRR | APIC_SEND_PENDING; | ||
271 | value = SET_APIC_DELIVERY_MODE(value, APIC_MODE_NMI); | ||
272 | apic_write(APIC_LVT1, value); | ||
273 | } | ||
274 | |||
275 | void disable_local_APIC(void) | 575 | void disable_local_APIC(void) |
276 | { | 576 | { |
277 | unsigned int value; | 577 | unsigned int value; |
@@ -333,7 +633,7 @@ int __init verify_local_APIC(void) | |||
333 | reg1 = GET_APIC_VERSION(reg0); | 633 | reg1 = GET_APIC_VERSION(reg0); |
334 | if (reg1 == 0x00 || reg1 == 0xff) | 634 | if (reg1 == 0x00 || reg1 == 0xff) |
335 | return 0; | 635 | return 0; |
336 | reg1 = get_maxlvt(); | 636 | reg1 = lapic_get_maxlvt(); |
337 | if (reg1 < 0x02 || reg1 == 0xff) | 637 | if (reg1 < 0x02 || reg1 == 0xff) |
338 | return 0; | 638 | return 0; |
339 | 639 | ||
@@ -355,18 +655,20 @@ int __init verify_local_APIC(void) | |||
355 | * compatibility mode, but most boxes are anymore. | 655 | * compatibility mode, but most boxes are anymore. |
356 | */ | 656 | */ |
357 | reg0 = apic_read(APIC_LVT0); | 657 | reg0 = apic_read(APIC_LVT0); |
358 | apic_printk(APIC_DEBUG,"Getting LVT0: %x\n", reg0); | 658 | apic_printk(APIC_DEBUG, "Getting LVT0: %x\n", reg0); |
359 | reg1 = apic_read(APIC_LVT1); | 659 | reg1 = apic_read(APIC_LVT1); |
360 | apic_printk(APIC_DEBUG, "Getting LVT1: %x\n", reg1); | 660 | apic_printk(APIC_DEBUG, "Getting LVT1: %x\n", reg1); |
361 | 661 | ||
362 | return 1; | 662 | return 1; |
363 | } | 663 | } |
364 | 664 | ||
665 | /** | ||
666 | * sync_Arb_IDs - synchronize APIC bus arbitration IDs | ||
667 | */ | ||
365 | void __init sync_Arb_IDs(void) | 668 | void __init sync_Arb_IDs(void) |
366 | { | 669 | { |
367 | /* Unsupported on P4 - see Intel Dev. Manual Vol. 3, Ch. 8.6.1 */ | 670 | /* Unsupported on P4 - see Intel Dev. Manual Vol. 3, Ch. 8.6.1 */ |
368 | unsigned int ver = GET_APIC_VERSION(apic_read(APIC_LVR)); | 671 | if (modern_apic()) |
369 | if (ver >= 0x14) /* P4 or higher */ | ||
370 | return; | 672 | return; |
371 | 673 | ||
372 | /* | 674 | /* |
@@ -418,9 +720,12 @@ void __init init_bsp_APIC(void) | |||
418 | apic_write(APIC_LVT1, value); | 720 | apic_write(APIC_LVT1, value); |
419 | } | 721 | } |
420 | 722 | ||
421 | void __cpuinit setup_local_APIC (void) | 723 | /** |
724 | * setup_local_APIC - setup the local APIC | ||
725 | */ | ||
726 | void __cpuinit setup_local_APIC(void) | ||
422 | { | 727 | { |
423 | unsigned int value, maxlvt; | 728 | unsigned int value; |
424 | int i, j; | 729 | int i, j; |
425 | 730 | ||
426 | value = apic_read(APIC_LVR); | 731 | value = apic_read(APIC_LVR); |
@@ -516,30 +821,217 @@ void __cpuinit setup_local_APIC (void) | |||
516 | else | 821 | else |
517 | value = APIC_DM_NMI | APIC_LVT_MASKED; | 822 | value = APIC_DM_NMI | APIC_LVT_MASKED; |
518 | apic_write(APIC_LVT1, value); | 823 | apic_write(APIC_LVT1, value); |
824 | } | ||
519 | 825 | ||
520 | { | 826 | void __cpuinit lapic_setup_esr(void) |
521 | unsigned oldvalue; | 827 | { |
522 | maxlvt = get_maxlvt(); | 828 | unsigned maxlvt = lapic_get_maxlvt(); |
523 | oldvalue = apic_read(APIC_ESR); | 829 | |
524 | value = ERROR_APIC_VECTOR; // enables sending errors | 830 | apic_write(APIC_LVTERR, ERROR_APIC_VECTOR); |
525 | apic_write(APIC_LVTERR, value); | 831 | /* |
526 | /* | 832 | * spec says clear errors after enabling vector. |
527 | * spec says clear errors after enabling vector. | 833 | */ |
528 | */ | 834 | if (maxlvt > 3) |
529 | if (maxlvt > 3) | 835 | apic_write(APIC_ESR, 0); |
530 | apic_write(APIC_ESR, 0); | 836 | } |
531 | value = apic_read(APIC_ESR); | ||
532 | if (value != oldvalue) | ||
533 | apic_printk(APIC_VERBOSE, | ||
534 | "ESR value after enabling vector: %08x, after %08x\n", | ||
535 | oldvalue, value); | ||
536 | } | ||
537 | 837 | ||
838 | void __cpuinit end_local_APIC_setup(void) | ||
839 | { | ||
840 | lapic_setup_esr(); | ||
538 | nmi_watchdog_default(); | 841 | nmi_watchdog_default(); |
539 | setup_apic_nmi_watchdog(NULL); | 842 | setup_apic_nmi_watchdog(NULL); |
540 | apic_pm_activate(); | 843 | apic_pm_activate(); |
541 | } | 844 | } |
542 | 845 | ||
846 | /* | ||
847 | * Detect and enable local APICs on non-SMP boards. | ||
848 | * Original code written by Keir Fraser. | ||
849 | * On AMD64 we trust the BIOS - if it says no APIC it is likely | ||
850 | * not correctly set up (usually the APIC timer won't work etc.) | ||
851 | */ | ||
852 | static int __init detect_init_APIC(void) | ||
853 | { | ||
854 | if (!cpu_has_apic) { | ||
855 | printk(KERN_INFO "No local APIC present\n"); | ||
856 | return -1; | ||
857 | } | ||
858 | |||
859 | mp_lapic_addr = APIC_DEFAULT_PHYS_BASE; | ||
860 | boot_cpu_id = 0; | ||
861 | return 0; | ||
862 | } | ||
863 | |||
864 | /** | ||
865 | * init_apic_mappings - initialize APIC mappings | ||
866 | */ | ||
867 | void __init init_apic_mappings(void) | ||
868 | { | ||
869 | /* | ||
870 | * If no local APIC can be found then set up a fake all | ||
871 | * zeroes page to simulate the local APIC and another | ||
872 | * one for the IO-APIC. | ||
873 | */ | ||
874 | if (!smp_found_config && detect_init_APIC()) { | ||
875 | apic_phys = (unsigned long) alloc_bootmem_pages(PAGE_SIZE); | ||
876 | apic_phys = __pa(apic_phys); | ||
877 | } else | ||
878 | apic_phys = mp_lapic_addr; | ||
879 | |||
880 | set_fixmap_nocache(FIX_APIC_BASE, apic_phys); | ||
881 | apic_printk(APIC_VERBOSE, "mapped APIC to %16lx (%16lx)\n", | ||
882 | APIC_BASE, apic_phys); | ||
883 | |||
884 | /* Put local APIC into the resource map. */ | ||
885 | lapic_resource.start = apic_phys; | ||
886 | lapic_resource.end = lapic_resource.start + PAGE_SIZE - 1; | ||
887 | insert_resource(&iomem_resource, &lapic_resource); | ||
888 | |||
889 | /* | ||
890 | * Fetch the APIC ID of the BSP in case we have a | ||
891 | * default configuration (or the MP table is broken). | ||
892 | */ | ||
893 | boot_cpu_id = GET_APIC_ID(apic_read(APIC_ID)); | ||
894 | } | ||
895 | |||
896 | /* | ||
897 | * This initializes the IO-APIC and APIC hardware if this is | ||
898 | * a UP kernel. | ||
899 | */ | ||
900 | int __init APIC_init_uniprocessor(void) | ||
901 | { | ||
902 | if (disable_apic) { | ||
903 | printk(KERN_INFO "Apic disabled\n"); | ||
904 | return -1; | ||
905 | } | ||
906 | if (!cpu_has_apic) { | ||
907 | disable_apic = 1; | ||
908 | printk(KERN_INFO "Apic disabled by BIOS\n"); | ||
909 | return -1; | ||
910 | } | ||
911 | |||
912 | verify_local_APIC(); | ||
913 | |||
914 | phys_cpu_present_map = physid_mask_of_physid(boot_cpu_id); | ||
915 | apic_write(APIC_ID, SET_APIC_ID(boot_cpu_id)); | ||
916 | |||
917 | setup_local_APIC(); | ||
918 | |||
919 | /* | ||
920 | * Now enable IO-APICs, actually call clear_IO_APIC | ||
921 | * We need clear_IO_APIC before enabling vector on BP | ||
922 | */ | ||
923 | if (!skip_ioapic_setup && nr_ioapics) | ||
924 | enable_IO_APIC(); | ||
925 | |||
926 | end_local_APIC_setup(); | ||
927 | |||
928 | if (smp_found_config && !skip_ioapic_setup && nr_ioapics) | ||
929 | setup_IO_APIC(); | ||
930 | else | ||
931 | nr_ioapics = 0; | ||
932 | setup_boot_APIC_clock(); | ||
933 | check_nmi_watchdog(); | ||
934 | return 0; | ||
935 | } | ||
936 | |||
937 | /* | ||
938 | * Local APIC interrupts | ||
939 | */ | ||
940 | |||
941 | /* | ||
942 | * This interrupt should _never_ happen with our APIC/SMP architecture | ||
943 | */ | ||
944 | asmlinkage void smp_spurious_interrupt(void) | ||
945 | { | ||
946 | unsigned int v; | ||
947 | exit_idle(); | ||
948 | irq_enter(); | ||
949 | /* | ||
950 | * Check if this really is a spurious interrupt and ACK it | ||
951 | * if it is a vectored one. Just in case... | ||
952 | * Spurious interrupts should not be ACKed. | ||
953 | */ | ||
954 | v = apic_read(APIC_ISR + ((SPURIOUS_APIC_VECTOR & ~0x1f) >> 1)); | ||
955 | if (v & (1 << (SPURIOUS_APIC_VECTOR & 0x1f))) | ||
956 | ack_APIC_irq(); | ||
957 | |||
958 | add_pda(irq_spurious_count, 1); | ||
959 | irq_exit(); | ||
960 | } | ||
961 | |||
962 | /* | ||
963 | * This interrupt should never happen with our APIC/SMP architecture | ||
964 | */ | ||
965 | asmlinkage void smp_error_interrupt(void) | ||
966 | { | ||
967 | unsigned int v, v1; | ||
968 | |||
969 | exit_idle(); | ||
970 | irq_enter(); | ||
971 | /* First tickle the hardware, only then report what went on. -- REW */ | ||
972 | v = apic_read(APIC_ESR); | ||
973 | apic_write(APIC_ESR, 0); | ||
974 | v1 = apic_read(APIC_ESR); | ||
975 | ack_APIC_irq(); | ||
976 | atomic_inc(&irq_err_count); | ||
977 | |||
978 | /* Here is what the APIC error bits mean: | ||
979 | 0: Send CS error | ||
980 | 1: Receive CS error | ||
981 | 2: Send accept error | ||
982 | 3: Receive accept error | ||
983 | 4: Reserved | ||
984 | 5: Send illegal vector | ||
985 | 6: Received illegal vector | ||
986 | 7: Illegal register address | ||
987 | */ | ||
988 | printk(KERN_DEBUG "APIC error on CPU%d: %02x(%02x)\n", | ||
989 | smp_processor_id(), v , v1); | ||
990 | irq_exit(); | ||
991 | } | ||
992 | |||
993 | void disconnect_bsp_APIC(int virt_wire_setup) | ||
994 | { | ||
995 | /* Go back to Virtual Wire compatibility mode */ | ||
996 | unsigned long value; | ||
997 | |||
998 | /* For the spurious interrupt use vector F, and enable it */ | ||
999 | value = apic_read(APIC_SPIV); | ||
1000 | value &= ~APIC_VECTOR_MASK; | ||
1001 | value |= APIC_SPIV_APIC_ENABLED; | ||
1002 | value |= 0xf; | ||
1003 | apic_write(APIC_SPIV, value); | ||
1004 | |||
1005 | if (!virt_wire_setup) { | ||
1006 | /* | ||
1007 | * For LVT0 make it edge triggered, active high, | ||
1008 | * external and enabled | ||
1009 | */ | ||
1010 | value = apic_read(APIC_LVT0); | ||
1011 | value &= ~(APIC_MODE_MASK | APIC_SEND_PENDING | | ||
1012 | APIC_INPUT_POLARITY | APIC_LVT_REMOTE_IRR | | ||
1013 | APIC_LVT_LEVEL_TRIGGER | APIC_LVT_MASKED); | ||
1014 | value |= APIC_LVT_REMOTE_IRR | APIC_SEND_PENDING; | ||
1015 | value = SET_APIC_DELIVERY_MODE(value, APIC_MODE_EXTINT); | ||
1016 | apic_write(APIC_LVT0, value); | ||
1017 | } else { | ||
1018 | /* Disable LVT0 */ | ||
1019 | apic_write(APIC_LVT0, APIC_LVT_MASKED); | ||
1020 | } | ||
1021 | |||
1022 | /* For LVT1 make it edge triggered, active high, nmi and enabled */ | ||
1023 | value = apic_read(APIC_LVT1); | ||
1024 | value &= ~(APIC_MODE_MASK | APIC_SEND_PENDING | | ||
1025 | APIC_INPUT_POLARITY | APIC_LVT_REMOTE_IRR | | ||
1026 | APIC_LVT_LEVEL_TRIGGER | APIC_LVT_MASKED); | ||
1027 | value |= APIC_LVT_REMOTE_IRR | APIC_SEND_PENDING; | ||
1028 | value = SET_APIC_DELIVERY_MODE(value, APIC_MODE_NMI); | ||
1029 | apic_write(APIC_LVT1, value); | ||
1030 | } | ||
1031 | |||
1032 | /* | ||
1033 | * Power management | ||
1034 | */ | ||
543 | #ifdef CONFIG_PM | 1035 | #ifdef CONFIG_PM |
544 | 1036 | ||
545 | static struct { | 1037 | static struct { |
@@ -571,7 +1063,7 @@ static int lapic_suspend(struct sys_device *dev, pm_message_t state) | |||
571 | if (!apic_pm_state.active) | 1063 | if (!apic_pm_state.active) |
572 | return 0; | 1064 | return 0; |
573 | 1065 | ||
574 | maxlvt = get_maxlvt(); | 1066 | maxlvt = lapic_get_maxlvt(); |
575 | 1067 | ||
576 | apic_pm_state.apic_id = apic_read(APIC_ID); | 1068 | apic_pm_state.apic_id = apic_read(APIC_ID); |
577 | apic_pm_state.apic_taskpri = apic_read(APIC_TASKPRI); | 1069 | apic_pm_state.apic_taskpri = apic_read(APIC_TASKPRI); |
@@ -605,7 +1097,7 @@ static int lapic_resume(struct sys_device *dev) | |||
605 | if (!apic_pm_state.active) | 1097 | if (!apic_pm_state.active) |
606 | return 0; | 1098 | return 0; |
607 | 1099 | ||
608 | maxlvt = get_maxlvt(); | 1100 | maxlvt = lapic_get_maxlvt(); |
609 | 1101 | ||
610 | local_irq_save(flags); | 1102 | local_irq_save(flags); |
611 | rdmsr(MSR_IA32_APICBASE, l, h); | 1103 | rdmsr(MSR_IA32_APICBASE, l, h); |
@@ -639,14 +1131,14 @@ static int lapic_resume(struct sys_device *dev) | |||
639 | } | 1131 | } |
640 | 1132 | ||
641 | static struct sysdev_class lapic_sysclass = { | 1133 | static struct sysdev_class lapic_sysclass = { |
642 | set_kset_name("lapic"), | 1134 | .name = "lapic", |
643 | .resume = lapic_resume, | 1135 | .resume = lapic_resume, |
644 | .suspend = lapic_suspend, | 1136 | .suspend = lapic_suspend, |
645 | }; | 1137 | }; |
646 | 1138 | ||
647 | static struct sys_device device_lapic = { | 1139 | static struct sys_device device_lapic = { |
648 | .id = 0, | 1140 | .id = 0, |
649 | .cls = &lapic_sysclass, | 1141 | .cls = &lapic_sysclass, |
650 | }; | 1142 | }; |
651 | 1143 | ||
652 | static void __cpuinit apic_pm_activate(void) | 1144 | static void __cpuinit apic_pm_activate(void) |
@@ -657,9 +1149,11 @@ static void __cpuinit apic_pm_activate(void) | |||
657 | static int __init init_lapic_sysfs(void) | 1149 | static int __init init_lapic_sysfs(void) |
658 | { | 1150 | { |
659 | int error; | 1151 | int error; |
1152 | |||
660 | if (!cpu_has_apic) | 1153 | if (!cpu_has_apic) |
661 | return 0; | 1154 | return 0; |
662 | /* XXX: remove suspend/resume procs if !apic_pm_state.active? */ | 1155 | /* XXX: remove suspend/resume procs if !apic_pm_state.active? */ |
1156 | |||
663 | error = sysdev_class_register(&lapic_sysclass); | 1157 | error = sysdev_class_register(&lapic_sysclass); |
664 | if (!error) | 1158 | if (!error) |
665 | error = sysdev_register(&device_lapic); | 1159 | error = sysdev_register(&device_lapic); |
@@ -673,423 +1167,6 @@ static void apic_pm_activate(void) { } | |||
673 | 1167 | ||
674 | #endif /* CONFIG_PM */ | 1168 | #endif /* CONFIG_PM */ |
675 | 1169 | ||
676 | static int __init apic_set_verbosity(char *str) | ||
677 | { | ||
678 | if (str == NULL) { | ||
679 | skip_ioapic_setup = 0; | ||
680 | ioapic_force = 1; | ||
681 | return 0; | ||
682 | } | ||
683 | if (strcmp("debug", str) == 0) | ||
684 | apic_verbosity = APIC_DEBUG; | ||
685 | else if (strcmp("verbose", str) == 0) | ||
686 | apic_verbosity = APIC_VERBOSE; | ||
687 | else { | ||
688 | printk(KERN_WARNING "APIC Verbosity level %s not recognised" | ||
689 | " use apic=verbose or apic=debug\n", str); | ||
690 | return -EINVAL; | ||
691 | } | ||
692 | |||
693 | return 0; | ||
694 | } | ||
695 | early_param("apic", apic_set_verbosity); | ||
696 | |||
697 | /* | ||
698 | * Detect and enable local APICs on non-SMP boards. | ||
699 | * Original code written by Keir Fraser. | ||
700 | * On AMD64 we trust the BIOS - if it says no APIC it is likely | ||
701 | * not correctly set up (usually the APIC timer won't work etc.) | ||
702 | */ | ||
703 | |||
704 | static int __init detect_init_APIC (void) | ||
705 | { | ||
706 | if (!cpu_has_apic) { | ||
707 | printk(KERN_INFO "No local APIC present\n"); | ||
708 | return -1; | ||
709 | } | ||
710 | |||
711 | mp_lapic_addr = APIC_DEFAULT_PHYS_BASE; | ||
712 | boot_cpu_id = 0; | ||
713 | return 0; | ||
714 | } | ||
715 | |||
716 | #ifdef CONFIG_X86_IO_APIC | ||
717 | static struct resource * __init ioapic_setup_resources(void) | ||
718 | { | ||
719 | #define IOAPIC_RESOURCE_NAME_SIZE 11 | ||
720 | unsigned long n; | ||
721 | struct resource *res; | ||
722 | char *mem; | ||
723 | int i; | ||
724 | |||
725 | if (nr_ioapics <= 0) | ||
726 | return NULL; | ||
727 | |||
728 | n = IOAPIC_RESOURCE_NAME_SIZE + sizeof(struct resource); | ||
729 | n *= nr_ioapics; | ||
730 | |||
731 | mem = alloc_bootmem(n); | ||
732 | res = (void *)mem; | ||
733 | |||
734 | if (mem != NULL) { | ||
735 | memset(mem, 0, n); | ||
736 | mem += sizeof(struct resource) * nr_ioapics; | ||
737 | |||
738 | for (i = 0; i < nr_ioapics; i++) { | ||
739 | res[i].name = mem; | ||
740 | res[i].flags = IORESOURCE_MEM | IORESOURCE_BUSY; | ||
741 | sprintf(mem, "IOAPIC %u", i); | ||
742 | mem += IOAPIC_RESOURCE_NAME_SIZE; | ||
743 | } | ||
744 | } | ||
745 | |||
746 | ioapic_resources = res; | ||
747 | |||
748 | return res; | ||
749 | } | ||
750 | |||
751 | static int __init ioapic_insert_resources(void) | ||
752 | { | ||
753 | int i; | ||
754 | struct resource *r = ioapic_resources; | ||
755 | |||
756 | if (!r) { | ||
757 | printk("IO APIC resources could be not be allocated.\n"); | ||
758 | return -1; | ||
759 | } | ||
760 | |||
761 | for (i = 0; i < nr_ioapics; i++) { | ||
762 | insert_resource(&iomem_resource, r); | ||
763 | r++; | ||
764 | } | ||
765 | |||
766 | return 0; | ||
767 | } | ||
768 | |||
769 | /* Insert the IO APIC resources after PCI initialization has occured to handle | ||
770 | * IO APICS that are mapped in on a BAR in PCI space. */ | ||
771 | late_initcall(ioapic_insert_resources); | ||
772 | #endif | ||
773 | |||
774 | void __init init_apic_mappings(void) | ||
775 | { | ||
776 | unsigned long apic_phys; | ||
777 | |||
778 | /* | ||
779 | * If no local APIC can be found then set up a fake all | ||
780 | * zeroes page to simulate the local APIC and another | ||
781 | * one for the IO-APIC. | ||
782 | */ | ||
783 | if (!smp_found_config && detect_init_APIC()) { | ||
784 | apic_phys = (unsigned long) alloc_bootmem_pages(PAGE_SIZE); | ||
785 | apic_phys = __pa(apic_phys); | ||
786 | } else | ||
787 | apic_phys = mp_lapic_addr; | ||
788 | |||
789 | set_fixmap_nocache(FIX_APIC_BASE, apic_phys); | ||
790 | apic_printk(APIC_VERBOSE, "mapped APIC to %16lx (%16lx)\n", | ||
791 | APIC_BASE, apic_phys); | ||
792 | |||
793 | /* Put local APIC into the resource map. */ | ||
794 | lapic_resource.start = apic_phys; | ||
795 | lapic_resource.end = lapic_resource.start + PAGE_SIZE - 1; | ||
796 | insert_resource(&iomem_resource, &lapic_resource); | ||
797 | |||
798 | /* | ||
799 | * Fetch the APIC ID of the BSP in case we have a | ||
800 | * default configuration (or the MP table is broken). | ||
801 | */ | ||
802 | boot_cpu_id = GET_APIC_ID(apic_read(APIC_ID)); | ||
803 | |||
804 | { | ||
805 | unsigned long ioapic_phys, idx = FIX_IO_APIC_BASE_0; | ||
806 | int i; | ||
807 | struct resource *ioapic_res; | ||
808 | |||
809 | ioapic_res = ioapic_setup_resources(); | ||
810 | for (i = 0; i < nr_ioapics; i++) { | ||
811 | if (smp_found_config) { | ||
812 | ioapic_phys = mp_ioapics[i].mpc_apicaddr; | ||
813 | } else { | ||
814 | ioapic_phys = (unsigned long) | ||
815 | alloc_bootmem_pages(PAGE_SIZE); | ||
816 | ioapic_phys = __pa(ioapic_phys); | ||
817 | } | ||
818 | set_fixmap_nocache(idx, ioapic_phys); | ||
819 | apic_printk(APIC_VERBOSE, | ||
820 | "mapped IOAPIC to %016lx (%016lx)\n", | ||
821 | __fix_to_virt(idx), ioapic_phys); | ||
822 | idx++; | ||
823 | |||
824 | if (ioapic_res != NULL) { | ||
825 | ioapic_res->start = ioapic_phys; | ||
826 | ioapic_res->end = ioapic_phys + (4 * 1024) - 1; | ||
827 | ioapic_res++; | ||
828 | } | ||
829 | } | ||
830 | } | ||
831 | } | ||
832 | |||
833 | /* | ||
834 | * This function sets up the local APIC timer, with a timeout of | ||
835 | * 'clocks' APIC bus clock. During calibration we actually call | ||
836 | * this function twice on the boot CPU, once with a bogus timeout | ||
837 | * value, second time for real. The other (noncalibrating) CPUs | ||
838 | * call this function only once, with the real, calibrated value. | ||
839 | * | ||
840 | * We do reads before writes even if unnecessary, to get around the | ||
841 | * P5 APIC double write bug. | ||
842 | */ | ||
843 | |||
844 | static void __setup_APIC_LVTT(unsigned int clocks, int oneshot, int irqen) | ||
845 | { | ||
846 | unsigned int lvtt_value, tmp_value; | ||
847 | |||
848 | lvtt_value = LOCAL_TIMER_VECTOR; | ||
849 | if (!oneshot) | ||
850 | lvtt_value |= APIC_LVT_TIMER_PERIODIC; | ||
851 | if (!irqen) | ||
852 | lvtt_value |= APIC_LVT_MASKED; | ||
853 | |||
854 | apic_write(APIC_LVTT, lvtt_value); | ||
855 | |||
856 | /* | ||
857 | * Divide PICLK by 16 | ||
858 | */ | ||
859 | tmp_value = apic_read(APIC_TDCR); | ||
860 | apic_write(APIC_TDCR, (tmp_value | ||
861 | & ~(APIC_TDR_DIV_1 | APIC_TDR_DIV_TMBASE)) | ||
862 | | APIC_TDR_DIV_16); | ||
863 | |||
864 | if (!oneshot) | ||
865 | apic_write(APIC_TMICT, clocks); | ||
866 | } | ||
867 | |||
868 | static void setup_APIC_timer(void) | ||
869 | { | ||
870 | struct clock_event_device *levt = &__get_cpu_var(lapic_events); | ||
871 | |||
872 | memcpy(levt, &lapic_clockevent, sizeof(*levt)); | ||
873 | levt->cpumask = cpumask_of_cpu(smp_processor_id()); | ||
874 | |||
875 | clockevents_register_device(levt); | ||
876 | } | ||
877 | |||
878 | /* | ||
879 | * In this function we calibrate APIC bus clocks to the external | ||
880 | * timer. Unfortunately we cannot use jiffies and the timer irq | ||
881 | * to calibrate, since some later bootup code depends on getting | ||
882 | * the first irq? Ugh. | ||
883 | * | ||
884 | * We want to do the calibration only once since we | ||
885 | * want to have local timer irqs syncron. CPUs connected | ||
886 | * by the same APIC bus have the very same bus frequency. | ||
887 | * And we want to have irqs off anyways, no accidental | ||
888 | * APIC irq that way. | ||
889 | */ | ||
890 | |||
891 | #define TICK_COUNT 100000000 | ||
892 | |||
893 | static void __init calibrate_APIC_clock(void) | ||
894 | { | ||
895 | unsigned apic, apic_start; | ||
896 | unsigned long tsc, tsc_start; | ||
897 | int result; | ||
898 | |||
899 | local_irq_disable(); | ||
900 | |||
901 | /* | ||
902 | * Put whatever arbitrary (but long enough) timeout | ||
903 | * value into the APIC clock, we just want to get the | ||
904 | * counter running for calibration. | ||
905 | * | ||
906 | * No interrupt enable ! | ||
907 | */ | ||
908 | __setup_APIC_LVTT(250000000, 0, 0); | ||
909 | |||
910 | apic_start = apic_read(APIC_TMCCT); | ||
911 | #ifdef CONFIG_X86_PM_TIMER | ||
912 | if (apic_calibrate_pmtmr && pmtmr_ioport) { | ||
913 | pmtimer_wait(5000); /* 5ms wait */ | ||
914 | apic = apic_read(APIC_TMCCT); | ||
915 | result = (apic_start - apic) * 1000L / 5; | ||
916 | } else | ||
917 | #endif | ||
918 | { | ||
919 | rdtscll(tsc_start); | ||
920 | |||
921 | do { | ||
922 | apic = apic_read(APIC_TMCCT); | ||
923 | rdtscll(tsc); | ||
924 | } while ((tsc - tsc_start) < TICK_COUNT && | ||
925 | (apic_start - apic) < TICK_COUNT); | ||
926 | |||
927 | result = (apic_start - apic) * 1000L * tsc_khz / | ||
928 | (tsc - tsc_start); | ||
929 | } | ||
930 | |||
931 | local_irq_enable(); | ||
932 | |||
933 | printk(KERN_DEBUG "APIC timer calibration result %d\n", result); | ||
934 | |||
935 | printk(KERN_INFO "Detected %d.%03d MHz APIC timer.\n", | ||
936 | result / 1000 / 1000, result / 1000 % 1000); | ||
937 | |||
938 | /* Calculate the scaled math multiplication factor */ | ||
939 | lapic_clockevent.mult = div_sc(result, NSEC_PER_SEC, 32); | ||
940 | lapic_clockevent.max_delta_ns = | ||
941 | clockevent_delta2ns(0x7FFFFF, &lapic_clockevent); | ||
942 | lapic_clockevent.min_delta_ns = | ||
943 | clockevent_delta2ns(0xF, &lapic_clockevent); | ||
944 | |||
945 | calibration_result = result / HZ; | ||
946 | } | ||
947 | |||
948 | void __init setup_boot_APIC_clock (void) | ||
949 | { | ||
950 | /* | ||
951 | * The local apic timer can be disabled via the kernel commandline. | ||
952 | * Register the lapic timer as a dummy clock event source on SMP | ||
953 | * systems, so the broadcast mechanism is used. On UP systems simply | ||
954 | * ignore it. | ||
955 | */ | ||
956 | if (disable_apic_timer) { | ||
957 | printk(KERN_INFO "Disabling APIC timer\n"); | ||
958 | /* No broadcast on UP ! */ | ||
959 | if (num_possible_cpus() > 1) | ||
960 | setup_APIC_timer(); | ||
961 | return; | ||
962 | } | ||
963 | |||
964 | printk(KERN_INFO "Using local APIC timer interrupts.\n"); | ||
965 | calibrate_APIC_clock(); | ||
966 | |||
967 | /* | ||
968 | * If nmi_watchdog is set to IO_APIC, we need the | ||
969 | * PIT/HPET going. Otherwise register lapic as a dummy | ||
970 | * device. | ||
971 | */ | ||
972 | if (nmi_watchdog != NMI_IO_APIC) | ||
973 | lapic_clockevent.features &= ~CLOCK_EVT_FEAT_DUMMY; | ||
974 | else | ||
975 | printk(KERN_WARNING "APIC timer registered as dummy," | ||
976 | " due to nmi_watchdog=1!\n"); | ||
977 | |||
978 | setup_APIC_timer(); | ||
979 | } | ||
980 | |||
981 | /* | ||
982 | * AMD C1E enabled CPUs have a real nasty problem: Some BIOSes set the | ||
983 | * C1E flag only in the secondary CPU, so when we detect the wreckage | ||
984 | * we already have enabled the boot CPU local apic timer. Check, if | ||
985 | * disable_apic_timer is set and the DUMMY flag is cleared. If yes, | ||
986 | * set the DUMMY flag again and force the broadcast mode in the | ||
987 | * clockevents layer. | ||
988 | */ | ||
989 | void __cpuinit check_boot_apic_timer_broadcast(void) | ||
990 | { | ||
991 | if (!disable_apic_timer || | ||
992 | (lapic_clockevent.features & CLOCK_EVT_FEAT_DUMMY)) | ||
993 | return; | ||
994 | |||
995 | printk(KERN_INFO "AMD C1E detected late. Force timer broadcast.\n"); | ||
996 | lapic_clockevent.features |= CLOCK_EVT_FEAT_DUMMY; | ||
997 | |||
998 | local_irq_enable(); | ||
999 | clockevents_notify(CLOCK_EVT_NOTIFY_BROADCAST_FORCE, &boot_cpu_id); | ||
1000 | local_irq_disable(); | ||
1001 | } | ||
1002 | |||
1003 | void __cpuinit setup_secondary_APIC_clock(void) | ||
1004 | { | ||
1005 | check_boot_apic_timer_broadcast(); | ||
1006 | setup_APIC_timer(); | ||
1007 | } | ||
1008 | |||
1009 | int setup_profiling_timer(unsigned int multiplier) | ||
1010 | { | ||
1011 | return -EINVAL; | ||
1012 | } | ||
1013 | |||
1014 | void setup_APIC_extended_lvt(unsigned char lvt_off, unsigned char vector, | ||
1015 | unsigned char msg_type, unsigned char mask) | ||
1016 | { | ||
1017 | unsigned long reg = (lvt_off << 4) + K8_APIC_EXT_LVT_BASE; | ||
1018 | unsigned int v = (mask << 16) | (msg_type << 8) | vector; | ||
1019 | apic_write(reg, v); | ||
1020 | } | ||
1021 | |||
1022 | /* | ||
1023 | * Local timer interrupt handler. It does both profiling and | ||
1024 | * process statistics/rescheduling. | ||
1025 | * | ||
1026 | * We do profiling in every local tick, statistics/rescheduling | ||
1027 | * happen only every 'profiling multiplier' ticks. The default | ||
1028 | * multiplier is 1 and it can be changed by writing the new multiplier | ||
1029 | * value into /proc/profile. | ||
1030 | */ | ||
1031 | |||
1032 | void smp_local_timer_interrupt(void) | ||
1033 | { | ||
1034 | int cpu = smp_processor_id(); | ||
1035 | struct clock_event_device *evt = &per_cpu(lapic_events, cpu); | ||
1036 | |||
1037 | /* | ||
1038 | * Normally we should not be here till LAPIC has been initialized but | ||
1039 | * in some cases like kdump, its possible that there is a pending LAPIC | ||
1040 | * timer interrupt from previous kernel's context and is delivered in | ||
1041 | * new kernel the moment interrupts are enabled. | ||
1042 | * | ||
1043 | * Interrupts are enabled early and LAPIC is setup much later, hence | ||
1044 | * its possible that when we get here evt->event_handler is NULL. | ||
1045 | * Check for event_handler being NULL and discard the interrupt as | ||
1046 | * spurious. | ||
1047 | */ | ||
1048 | if (!evt->event_handler) { | ||
1049 | printk(KERN_WARNING | ||
1050 | "Spurious LAPIC timer interrupt on cpu %d\n", cpu); | ||
1051 | /* Switch it off */ | ||
1052 | lapic_timer_setup(CLOCK_EVT_MODE_SHUTDOWN, evt); | ||
1053 | return; | ||
1054 | } | ||
1055 | |||
1056 | /* | ||
1057 | * the NMI deadlock-detector uses this. | ||
1058 | */ | ||
1059 | add_pda(apic_timer_irqs, 1); | ||
1060 | |||
1061 | evt->event_handler(evt); | ||
1062 | } | ||
1063 | |||
1064 | /* | ||
1065 | * Local APIC timer interrupt. This is the most natural way for doing | ||
1066 | * local interrupts, but local timer interrupts can be emulated by | ||
1067 | * broadcast interrupts too. [in case the hw doesn't support APIC timers] | ||
1068 | * | ||
1069 | * [ if a single-CPU system runs an SMP kernel then we call the local | ||
1070 | * interrupt as well. Thus we cannot inline the local irq ... ] | ||
1071 | */ | ||
1072 | void smp_apic_timer_interrupt(struct pt_regs *regs) | ||
1073 | { | ||
1074 | struct pt_regs *old_regs = set_irq_regs(regs); | ||
1075 | |||
1076 | /* | ||
1077 | * NOTE! We'd better ACK the irq immediately, | ||
1078 | * because timer handling can be slow. | ||
1079 | */ | ||
1080 | ack_APIC_irq(); | ||
1081 | /* | ||
1082 | * update_process_times() expects us to have done irq_enter(). | ||
1083 | * Besides, if we don't timer interrupts ignore the global | ||
1084 | * interrupt lock, which is the WrongThing (tm) to do. | ||
1085 | */ | ||
1086 | exit_idle(); | ||
1087 | irq_enter(); | ||
1088 | smp_local_timer_interrupt(); | ||
1089 | irq_exit(); | ||
1090 | set_irq_regs(old_regs); | ||
1091 | } | ||
1092 | |||
1093 | /* | 1170 | /* |
1094 | * apic_is_clustered_box() -- Check if we can expect good TSC | 1171 | * apic_is_clustered_box() -- Check if we can expect good TSC |
1095 | * | 1172 | * |
@@ -1103,21 +1180,34 @@ __cpuinit int apic_is_clustered_box(void) | |||
1103 | { | 1180 | { |
1104 | int i, clusters, zeros; | 1181 | int i, clusters, zeros; |
1105 | unsigned id; | 1182 | unsigned id; |
1183 | u16 *bios_cpu_apicid = x86_bios_cpu_apicid_early_ptr; | ||
1106 | DECLARE_BITMAP(clustermap, NUM_APIC_CLUSTERS); | 1184 | DECLARE_BITMAP(clustermap, NUM_APIC_CLUSTERS); |
1107 | 1185 | ||
1108 | bitmap_zero(clustermap, NUM_APIC_CLUSTERS); | 1186 | bitmap_zero(clustermap, NUM_APIC_CLUSTERS); |
1109 | 1187 | ||
1110 | for (i = 0; i < NR_CPUS; i++) { | 1188 | for (i = 0; i < NR_CPUS; i++) { |
1111 | id = bios_cpu_apicid[i]; | 1189 | /* are we being called early in kernel startup? */ |
1190 | if (bios_cpu_apicid) { | ||
1191 | id = bios_cpu_apicid[i]; | ||
1192 | } | ||
1193 | else if (i < nr_cpu_ids) { | ||
1194 | if (cpu_present(i)) | ||
1195 | id = per_cpu(x86_bios_cpu_apicid, i); | ||
1196 | else | ||
1197 | continue; | ||
1198 | } | ||
1199 | else | ||
1200 | break; | ||
1201 | |||
1112 | if (id != BAD_APICID) | 1202 | if (id != BAD_APICID) |
1113 | __set_bit(APIC_CLUSTERID(id), clustermap); | 1203 | __set_bit(APIC_CLUSTERID(id), clustermap); |
1114 | } | 1204 | } |
1115 | 1205 | ||
1116 | /* Problem: Partially populated chassis may not have CPUs in some of | 1206 | /* Problem: Partially populated chassis may not have CPUs in some of |
1117 | * the APIC clusters they have been allocated. Only present CPUs have | 1207 | * the APIC clusters they have been allocated. Only present CPUs have |
1118 | * bios_cpu_apicid entries, thus causing zeroes in the bitmap. Since | 1208 | * x86_bios_cpu_apicid entries, thus causing zeroes in the bitmap. |
1119 | * clusters are allocated sequentially, count zeros only if they are | 1209 | * Since clusters are allocated sequentially, count zeros only if |
1120 | * bounded by ones. | 1210 | * they are bounded by ones. |
1121 | */ | 1211 | */ |
1122 | clusters = 0; | 1212 | clusters = 0; |
1123 | zeros = 0; | 1213 | zeros = 0; |
@@ -1138,96 +1228,33 @@ __cpuinit int apic_is_clustered_box(void) | |||
1138 | } | 1228 | } |
1139 | 1229 | ||
1140 | /* | 1230 | /* |
1141 | * This interrupt should _never_ happen with our APIC/SMP architecture | 1231 | * APIC command line parameters |
1142 | */ | ||
1143 | asmlinkage void smp_spurious_interrupt(void) | ||
1144 | { | ||
1145 | unsigned int v; | ||
1146 | exit_idle(); | ||
1147 | irq_enter(); | ||
1148 | /* | ||
1149 | * Check if this really is a spurious interrupt and ACK it | ||
1150 | * if it is a vectored one. Just in case... | ||
1151 | * Spurious interrupts should not be ACKed. | ||
1152 | */ | ||
1153 | v = apic_read(APIC_ISR + ((SPURIOUS_APIC_VECTOR & ~0x1f) >> 1)); | ||
1154 | if (v & (1 << (SPURIOUS_APIC_VECTOR & 0x1f))) | ||
1155 | ack_APIC_irq(); | ||
1156 | |||
1157 | add_pda(irq_spurious_count, 1); | ||
1158 | irq_exit(); | ||
1159 | } | ||
1160 | |||
1161 | /* | ||
1162 | * This interrupt should never happen with our APIC/SMP architecture | ||
1163 | */ | 1232 | */ |
1164 | 1233 | static int __init apic_set_verbosity(char *str) | |
1165 | asmlinkage void smp_error_interrupt(void) | ||
1166 | { | ||
1167 | unsigned int v, v1; | ||
1168 | |||
1169 | exit_idle(); | ||
1170 | irq_enter(); | ||
1171 | /* First tickle the hardware, only then report what went on. -- REW */ | ||
1172 | v = apic_read(APIC_ESR); | ||
1173 | apic_write(APIC_ESR, 0); | ||
1174 | v1 = apic_read(APIC_ESR); | ||
1175 | ack_APIC_irq(); | ||
1176 | atomic_inc(&irq_err_count); | ||
1177 | |||
1178 | /* Here is what the APIC error bits mean: | ||
1179 | 0: Send CS error | ||
1180 | 1: Receive CS error | ||
1181 | 2: Send accept error | ||
1182 | 3: Receive accept error | ||
1183 | 4: Reserved | ||
1184 | 5: Send illegal vector | ||
1185 | 6: Received illegal vector | ||
1186 | 7: Illegal register address | ||
1187 | */ | ||
1188 | printk (KERN_DEBUG "APIC error on CPU%d: %02x(%02x)\n", | ||
1189 | smp_processor_id(), v , v1); | ||
1190 | irq_exit(); | ||
1191 | } | ||
1192 | |||
1193 | int disable_apic; | ||
1194 | |||
1195 | /* | ||
1196 | * This initializes the IO-APIC and APIC hardware if this is | ||
1197 | * a UP kernel. | ||
1198 | */ | ||
1199 | int __init APIC_init_uniprocessor (void) | ||
1200 | { | 1234 | { |
1201 | if (disable_apic) { | 1235 | if (str == NULL) { |
1202 | printk(KERN_INFO "Apic disabled\n"); | 1236 | skip_ioapic_setup = 0; |
1203 | return -1; | 1237 | ioapic_force = 1; |
1238 | return 0; | ||
1204 | } | 1239 | } |
1205 | if (!cpu_has_apic) { | 1240 | if (strcmp("debug", str) == 0) |
1206 | disable_apic = 1; | 1241 | apic_verbosity = APIC_DEBUG; |
1207 | printk(KERN_INFO "Apic disabled by BIOS\n"); | 1242 | else if (strcmp("verbose", str) == 0) |
1208 | return -1; | 1243 | apic_verbosity = APIC_VERBOSE; |
1244 | else { | ||
1245 | printk(KERN_WARNING "APIC Verbosity level %s not recognised" | ||
1246 | " use apic=verbose or apic=debug\n", str); | ||
1247 | return -EINVAL; | ||
1209 | } | 1248 | } |
1210 | 1249 | ||
1211 | verify_local_APIC(); | ||
1212 | |||
1213 | phys_cpu_present_map = physid_mask_of_physid(boot_cpu_id); | ||
1214 | apic_write(APIC_ID, SET_APIC_ID(boot_cpu_id)); | ||
1215 | |||
1216 | setup_local_APIC(); | ||
1217 | |||
1218 | if (smp_found_config && !skip_ioapic_setup && nr_ioapics) | ||
1219 | setup_IO_APIC(); | ||
1220 | else | ||
1221 | nr_ioapics = 0; | ||
1222 | setup_boot_APIC_clock(); | ||
1223 | check_nmi_watchdog(); | ||
1224 | return 0; | 1250 | return 0; |
1225 | } | 1251 | } |
1252 | early_param("apic", apic_set_verbosity); | ||
1226 | 1253 | ||
1227 | static __init int setup_disableapic(char *str) | 1254 | static __init int setup_disableapic(char *str) |
1228 | { | 1255 | { |
1229 | disable_apic = 1; | 1256 | disable_apic = 1; |
1230 | clear_bit(X86_FEATURE_APIC, boot_cpu_data.x86_capability); | 1257 | clear_cpu_cap(&boot_cpu_data, X86_FEATURE_APIC); |
1231 | return 0; | 1258 | return 0; |
1232 | } | 1259 | } |
1233 | early_param("disableapic", setup_disableapic); | 1260 | early_param("disableapic", setup_disableapic); |