Commit a5bfb7f3 authored by Andrew Morton's avatar Andrew Morton Committed by Linus Torvalds

[PATCH] Local APIC enable fixes

From: mikep@csd.uu.se

There has been a number of problem reports about local APIC
interacting badly with ACPI on P4s due to the P4 local APIC
force-enable change in 2.5.74,

This patch reverts the 2.5.74 patch, so if the BIOS disables
the local APIC on a P4, we don't enable it by default any more.

The rescue the situation for those P4 systems where the local
APIC _can_ be enabled safely, I've added two kernel parameters
that can be used to override broken BIOSen:
- "nolapic" prevents the kernel from enabling or using the local
  APIC. This is stronger than listing a machine in the DMI scan
  blacklist, since it also works for machines that boot with the
  local APIC already enabled.
- "lapic" tells the kernel to force-enable the P4 local APIC if
  the BIOS disabled it. I haven't changed the logic for P6/K7
  family processors, so we still force-enable those unless
  "nolapic" was passed to the kernel.

The patch also includes a cleanup: the dont_use_local_apic_timer
flag variable is not set any more since 2.5.74, so it's removed.
parent 14e902a4
......@@ -439,6 +439,8 @@ running once the system is up.
l2cr= [PPC]
lapic [IA-32,APIC] Enable the local APIC even if BIOS disabled it.
lasi= [HW,SCSI] PARISC LASI driver for the 53c700 chip
Format: addr:<io>,irq:<irq>
......@@ -626,6 +628,8 @@ running once the system is up.
nointroute [IA-64]
nolapic [IA-32,APIC] Do not enable or use the local APIC.
nomce [IA-32] Machine Check Exception
noresume [SWSUSP] Disables resume and restore original swap space.
......
......@@ -604,7 +604,26 @@ static void apic_pm_activate(void) { }
* Detect and enable local APICs on non-SMP boards.
* Original code written by Keir Fraser.
*/
int dont_enable_local_apic __initdata = 0;
/*
* Knob to control our willingness to enable the local APIC.
*/
int enable_local_apic __initdata = 0; /* -1=force-disable, +1=force-enable */
static int __init lapic_disable(char *str)
{
enable_local_apic = -1;
clear_bit(X86_FEATURE_APIC, boot_cpu_data.x86_capability);
return 0;
}
__setup("nolapic", lapic_disable);
static int __init lapic_enable(char *str)
{
enable_local_apic = 1;
return 0;
}
__setup("lapic", lapic_enable);
static int __init detect_init_APIC (void)
{
......@@ -612,7 +631,7 @@ static int __init detect_init_APIC (void)
extern void get_cpu_vendor(struct cpuinfo_x86*);
/* Disabled by DMI scan or kernel option? */
if (dont_enable_local_apic)
if (enable_local_apic < 0)
return -1;
/* Workaround for us being called before identify_cpu(). */
......@@ -626,7 +645,7 @@ static int __init detect_init_APIC (void)
goto no_apic;
case X86_VENDOR_INTEL:
if (boot_cpu_data.x86 == 6 ||
boot_cpu_data.x86 == 15 ||
(boot_cpu_data.x86 == 15 && (cpu_has_apic || enable_local_apic > 0)) ||
(boot_cpu_data.x86 == 5 && cpu_has_apic))
break;
goto no_apic;
......@@ -908,14 +927,8 @@ int __init calibrate_APIC_clock(void)
static unsigned int calibration_result;
int dont_use_local_apic_timer __initdata = 0;
void __init setup_boot_APIC_clock(void)
{
/* Disabled by DMI scan or kernel option? */
if (dont_use_local_apic_timer)
return;
printk("Using local APIC timer interrupts.\n");
using_apic_timer = 1;
......@@ -1132,6 +1145,9 @@ asmlinkage void smp_error_interrupt(void)
*/
int __init APIC_init_uniprocessor (void)
{
if (enable_local_apic < 0)
clear_bit(X86_FEATURE_APIC, boot_cpu_data.x86_capability);
if (!smp_found_config && !cpu_has_apic)
return -1;
......
......@@ -314,9 +314,9 @@ static __init int apm_is_horked(struct dmi_blacklist *d)
static int __init local_apic_kills_bios(struct dmi_blacklist *d)
{
#ifdef CONFIG_X86_LOCAL_APIC
extern int dont_enable_local_apic;
if (!dont_enable_local_apic) {
dont_enable_local_apic = 1;
extern int enable_local_apic;
if (enable_local_apic == 0) {
enable_local_apic = -1;
printk(KERN_WARNING "%s with broken BIOS detected. "
"Refusing to enable the local APIC.\n",
d->ident);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment