http://linux-acpi.bkbits.net/linux-acpi-test-2.6.7 len.brown@intel.com|ChangeSet|20040515031404|22650 len.brown # This is a BitKeeper generated diff -Nru style patch. # # ChangeSet # 2004/05/16 01:19:02-07:00 akpm@bix.(none) # Merge bix.(none):/usr/src/bk25 into bix.(none):/usr/src/bk-acpi # # arch/ia64/kernel/acpi.c # 2004/05/16 01:18:58-07:00 akpm@bix.(none) +0 -0 # Auto merged # # arch/i386/kernel/acpi/boot.c # 2004/05/16 01:18:58-07:00 akpm@bix.(none) +0 -0 # Auto merged # # ChangeSet # 2004/05/14 23:14:04-04:00 len.brown@intel.com # Merge intel.com:/home/lenb/src/linux-acpi-test-2.6.6 # into intel.com:/home/lenb/src/linux-acpi-test-2.6.7 # # arch/x86_64/kernel/io_apic.c # 2004/05/14 23:14:00-04:00 len.brown@intel.com +0 -0 # Auto merged # # ChangeSet # 2004/05/14 23:09:23-04:00 len.brown@intel.com # [ACPI] delete IOAPIC-disable workaround on x86_64/VIA # http://bugme.osdl.org/show_bug.cgi?id=1530 # # arch/x86_64/kernel/io_apic.c # 2004/05/14 23:09:16-04:00 len.brown@intel.com +1 -1 # delete IOAPIC-disable workaround on x86_64/VIA # # ChangeSet # 2004/05/13 00:10:47-04:00 len.brown@intel.com # [ACPI] create kacpid thread to handle ACPI work in process context. # Also will be needed for cpu hot-unplug. # from Anil S Keshavamurthy and David Shaohua Li # http://bugzilla.kernel.org/show_bug.cgi?id=2515 # # include/acpi/acpiosxf.h # 2004/04/19 23:34:36-04:00 len.brown@intel.com +4 -0 # create kacpid # # drivers/acpi/scan.c # 2004/04/19 23:34:36-04:00 len.brown@intel.com +2 -0 # create kacpid # # drivers/acpi/osl.c # 2004/04/19 23:33:26-04:00 len.brown@intel.com +14 -2 # create kacpid # # drivers/acpi/events/evxface.c # 2004/04/19 23:34:36-04:00 len.brown@intel.com +27 -0 # create kacpid # # drivers/acpi/acpi_ksyms.c # 2004/04/19 23:34:36-04:00 len.brown@intel.com +1 -1 # create kacpid # # ChangeSet # 2004/05/12 23:31:01-04:00 len.brown@intel.com # [ACPI] Add MADT error checking (Yi Zhu) # http://bugzilla.kernel.org/show_bug.cgi?id=1434 # # include/linux/acpi.h # 2004/05/12 23:30:55-04:00 len.brown@intel.com +1 -1 # Add MADT error checking # # drivers/acpi/tables.c # 2004/05/12 23:30:55-04:00 len.brown@intel.com +3 -2 # Add MADT error checking # # arch/ia64/kernel/acpi.c # 2004/05/12 23:30:55-04:00 len.brown@intel.com +27 -14 # Add MADT error checking # # arch/i386/kernel/acpi/boot.c # 2004/05/12 23:30:55-04:00 len.brown@intel.com +29 -13 # Add MADT error checking # # ChangeSet # 2004/05/12 01:57:31-04:00 len.brown@intel.com # Merge intel.com:/home/lenb/src/linux-acpi-test-2.6.6 # into intel.com:/home/lenb/src/linux-acpi-test-2.6.7 # # arch/i386/mach-es7000/es7000plat.c # 2004/05/12 01:57:24-04:00 len.brown@intel.com +0 -0 # Auto merged # # BitKeeper/deleted/.del-setup.c~1b687d49b2d0b042 # 2004/05/12 01:57:24-04:00 len.brown@intel.com +0 -0 # Auto merged # # arch/i386/mach-es7000/es7000plat.c # 2004/05/12 01:57:24-04:00 len.brown@intel.com +0 -0 # Merge rename: arch/i386/mach-es7000/es7000.c -> arch/i386/mach-es7000/es7000plat.c # # BitKeeper/deleted/.del-setup.c~1b687d49b2d0b042 # 2004/05/12 01:57:24-04:00 len.brown@intel.com +0 -0 # Merge rename: arch/i386/mach-es7000/setup.c -> BitKeeper/deleted/.del-setup.c~1b687d49b2d0b042 # # ChangeSet # 2004/05/12 00:37:02-04:00 len.brown@intel.com # [ACPI] if _STA.functional, set _STA.present (Bjorn Helgaas) # workaround for Big Sur and Bull systems # # drivers/acpi/bus.c # 2004/05/12 00:36:55-04:00 len.brown@intel.com +8 -0 # if _STA.functional, set _STA.present # workaround for Big Sur and Bull systems # # ChangeSet # 2004/05/11 23:53:05-04:00 len.brown@intel.com # [ACPI] create platform_rename_gsi() so ES7000 can munge IRQ numbers # from Natalie Protasevich # # arch/i386/mach-es7000/es7000.c # 2004/05/11 23:53:00-04:00 len.brown@intel.com +24 -0 # platform_rename_gsi = es7000_rename_gsi # # arch/i386/kernel/mpparse.c # 2004/05/11 23:53:00-04:00 len.brown@intel.com +4 -4 # call platform_rename_gsi() to allow ES7000 to munge IRQ#'s # # arch/i386/mach-es7000/setup.c # 2004/05/11 17:18:42-04:00 len.brown@intel.com +2 -1 # whitespace # diff -Nru a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c --- a/arch/i386/kernel/acpi/boot.c Sun May 16 01:20:47 2004 +++ b/arch/i386/kernel/acpi/boot.c Sun May 16 01:20:47 2004 @@ -51,6 +51,10 @@ #endif /* X86 */ +#define BAD_MADT_ENTRY(entry, end) ( \ + (!entry) || (unsigned long)entry + sizeof(*entry) > end || \ + ((acpi_table_entry_header *)entry)->length != sizeof(*entry)) + #define PREFIX "ACPI: " #ifdef CONFIG_ACPI_PCI @@ -204,12 +208,13 @@ static int __init acpi_parse_lapic ( - acpi_table_entry_header *header) + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_lapic *processor = NULL; processor = (struct acpi_table_lapic*) header; - if (!processor) + + if (BAD_MADT_ENTRY(processor, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -225,15 +230,15 @@ return 0; } - static int __init acpi_parse_lapic_addr_ovr ( - acpi_table_entry_header *header) + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_lapic_addr_ovr *lapic_addr_ovr = NULL; lapic_addr_ovr = (struct acpi_table_lapic_addr_ovr*) header; - if (!lapic_addr_ovr) + + if (BAD_MADT_ENTRY(lapic_addr_ovr, end)) return -EINVAL; acpi_lapic_addr = lapic_addr_ovr->address; @@ -243,12 +248,13 @@ static int __init acpi_parse_lapic_nmi ( - acpi_table_entry_header *header) + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_lapic_nmi *lapic_nmi = NULL; lapic_nmi = (struct acpi_table_lapic_nmi*) header; - if (!lapic_nmi) + + if (BAD_MADT_ENTRY(lapic_nmi, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -266,12 +272,13 @@ static int __init acpi_parse_ioapic ( - acpi_table_entry_header *header) + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_ioapic *ioapic = NULL; ioapic = (struct acpi_table_ioapic*) header; - if (!ioapic) + + if (BAD_MADT_ENTRY(ioapic, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -320,12 +327,13 @@ static int __init acpi_parse_int_src_ovr ( - acpi_table_entry_header *header) + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_int_src_ovr *intsrc = NULL; intsrc = (struct acpi_table_int_src_ovr*) header; - if (!intsrc) + + if (BAD_MADT_ENTRY(intsrc, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -354,12 +362,13 @@ static int __init acpi_parse_nmi_src ( - acpi_table_entry_header *header) + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_nmi_src *nmi_src = NULL; nmi_src = (struct acpi_table_nmi_src*) header; - if (!nmi_src) + + if (BAD_MADT_ENTRY(nmi_src, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -718,6 +727,13 @@ smp_found_config = 1; clustered_apic_check(); } + } + if (error == -EINVAL) { + /* + * Dell Precision Workstation 410, 610 come here. + */ + printk(KERN_ERR PREFIX "Invalid BIOS MADT, disabling ACPI\n"); + disable_acpi(); } } #endif diff -Nru a/arch/i386/kernel/mpparse.c b/arch/i386/kernel/mpparse.c --- a/arch/i386/kernel/mpparse.c Sun May 16 01:20:47 2004 +++ b/arch/i386/kernel/mpparse.c Sun May 16 01:20:47 2004 @@ -1029,6 +1029,8 @@ #ifdef CONFIG_ACPI_PCI +int (*platform_rename_gsi)(int ioapic, int gsi); + void __init mp_parse_prt (void) { struct list_head *node = NULL; @@ -1072,10 +1074,8 @@ continue; ioapic_pin = gsi - mp_ioapic_routing[ioapic].gsi_base; - if (es7000_plat) { - if (!ioapic && (gsi < 16)) - gsi += 16; - } + if (platform_rename_gsi) + gsi = platform_rename_gsi(ioapic, gsi); /* * Avoid pin reprogramming. PRTs typically include entries diff -Nru a/arch/i386/mach-es7000/es7000plat.c b/arch/i386/mach-es7000/es7000plat.c --- a/arch/i386/mach-es7000/es7000plat.c Sun May 16 01:20:47 2004 +++ b/arch/i386/mach-es7000/es7000plat.c Sun May 16 01:20:47 2004 @@ -50,6 +50,29 @@ struct mip_reg *host_reg; int mip_port; unsigned long mip_addr, host_addr; +extern int (*platform_rename_gsi)(); + +static int __init +es7000_rename_gsi(int ioapic, int gsi) +{ + if (ioapic) + return gsi; + else { + if (gsi == 0) + return 13; + if (gsi == 1) + return 16; + if (gsi == 4) + return 17; + if (gsi == 6) + return 18; + if (gsi == 7) + return 19; + if (gsi == 8) + return 20; + return gsi; + } +} /* * Parse the OEM Table @@ -116,6 +139,7 @@ } else { printk("\nEnabling ES7000 specific features...\n"); es7000_plat = 1; + platform_rename_gsi = es7000_rename_gsi; } return es7000_plat; } diff -Nru a/arch/ia64/kernel/acpi.c b/arch/ia64/kernel/acpi.c --- a/arch/ia64/kernel/acpi.c Sun May 16 01:20:47 2004 +++ b/arch/ia64/kernel/acpi.c Sun May 16 01:20:47 2004 @@ -52,6 +52,9 @@ #include #include +#define BAD_MADT_ENTRY(entry, end) ( \ + (!entry) || (unsigned long)entry + sizeof(*entry) > end || \ + ((acpi_table_entry_header *)entry)->length != sizeof(*entry)) #define PREFIX "ACPI: " @@ -158,12 +161,14 @@ static int __init -acpi_parse_lapic_addr_ovr (acpi_table_entry_header *header) +acpi_parse_lapic_addr_ovr ( + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_lapic_addr_ovr *lapic; lapic = (struct acpi_table_lapic_addr_ovr *) header; - if (!lapic) + + if (BAD_MADT_ENTRY(lapic, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -177,12 +182,13 @@ static int __init -acpi_parse_lsapic (acpi_table_entry_header *header) +acpi_parse_lsapic (acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_lsapic *lsapic; lsapic = (struct acpi_table_lsapic *) header; - if (!lsapic) + + if (BAD_MADT_ENTRY(lsapic, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -210,12 +216,13 @@ static int __init -acpi_parse_lapic_nmi (acpi_table_entry_header *header) +acpi_parse_lapic_nmi (acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_lapic_nmi *lacpi_nmi; lacpi_nmi = (struct acpi_table_lapic_nmi*) header; - if (!lacpi_nmi) + + if (BAD_MADT_ENTRY(lacpi_nmi, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -226,12 +233,13 @@ static int __init -acpi_parse_iosapic (acpi_table_entry_header *header) +acpi_parse_iosapic (acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_iosapic *iosapic; iosapic = (struct acpi_table_iosapic *) header; - if (!iosapic) + + if (BAD_MADT_ENTRY(iosapic, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -243,13 +251,15 @@ static int __init -acpi_parse_plat_int_src (acpi_table_entry_header *header) +acpi_parse_plat_int_src ( + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_plat_int_src *plintsrc; int vector; plintsrc = (struct acpi_table_plat_int_src *) header; - if (!plintsrc) + + if (BAD_MADT_ENTRY(plintsrc, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -272,12 +282,14 @@ static int __init -acpi_parse_int_src_ovr (acpi_table_entry_header *header) +acpi_parse_int_src_ovr ( + acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_int_src_ovr *p; p = (struct acpi_table_int_src_ovr *) header; - if (!p) + + if (BAD_MADT_ENTRY(p, end)) return -EINVAL; acpi_table_print_madt_entry(header); @@ -290,12 +302,13 @@ static int __init -acpi_parse_nmi_src (acpi_table_entry_header *header) +acpi_parse_nmi_src (acpi_table_entry_header *header, const unsigned long end) { struct acpi_table_nmi_src *nmi_src; nmi_src = (struct acpi_table_nmi_src*) header; - if (!nmi_src) + + if (BAD_MADT_ENTRY(nmi_src, end)) return -EINVAL; acpi_table_print_madt_entry(header); diff -Nru a/arch/x86_64/kernel/io_apic.c b/arch/x86_64/kernel/io_apic.c --- a/arch/x86_64/kernel/io_apic.c Sun May 16 01:20:47 2004 +++ b/arch/x86_64/kernel/io_apic.c Sun May 16 01:20:47 2004 @@ -259,7 +259,7 @@ iommu_aperture_disabled = 1; } #endif - /* FALL THROUGH */ + return; case PCI_VENDOR_ID_NVIDIA: #ifndef CONFIG_SMP printk(KERN_INFO diff -Nru a/drivers/acpi/acpi_ksyms.c b/drivers/acpi/acpi_ksyms.c --- a/drivers/acpi/acpi_ksyms.c Sun May 16 01:20:47 2004 +++ b/drivers/acpi/acpi_ksyms.c Sun May 16 01:20:47 2004 @@ -106,7 +106,7 @@ EXPORT_SYMBOL(acpi_os_create_semaphore); EXPORT_SYMBOL(acpi_os_delete_semaphore); EXPORT_SYMBOL(acpi_os_wait_semaphore); - +EXPORT_SYMBOL(acpi_os_wait_events_complete); EXPORT_SYMBOL(acpi_os_read_pci_configuration); /* ACPI Utilities (acpi_utils.c) */ diff -Nru a/drivers/acpi/bus.c b/drivers/acpi/bus.c --- a/drivers/acpi/bus.c Sun May 16 01:20:47 2004 +++ b/drivers/acpi/bus.c Sun May 16 01:20:47 2004 @@ -112,6 +112,14 @@ else STRUCT_TO_INT(device->status) = 0x0F; + if (device->status.functional && !device->status.present) { + printk(KERN_WARNING PREFIX "Device [%s] status [%08x]: " + "functional but not present; setting present\n", + device->pnp.bus_id, + (u32) STRUCT_TO_INT(device->status)); + device->status.present = 1; + } + ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Device [%s] status [%08x]\n", device->pnp.bus_id, (u32) STRUCT_TO_INT(device->status))); diff -Nru a/drivers/acpi/events/evxface.c b/drivers/acpi/events/evxface.c --- a/drivers/acpi/events/evxface.c Sun May 16 01:20:47 2004 +++ b/drivers/acpi/events/evxface.c Sun May 16 01:20:47 2004 @@ -406,6 +406,15 @@ goto unlock_and_exit; } + /* Make sure all deferred tasks are completed */ + + (void) acpi_ut_release_mutex (ACPI_MTX_NAMESPACE); + acpi_os_wait_events_complete(NULL); + status = acpi_ut_acquire_mutex (ACPI_MTX_NAMESPACE); + if (ACPI_FAILURE (status)) { + return_ACPI_STATUS (status); + } + if (handler_type == ACPI_SYSTEM_NOTIFY) { acpi_gbl_system_notify.node = NULL; acpi_gbl_system_notify.handler = NULL; @@ -452,6 +461,15 @@ goto unlock_and_exit; } + /* Make sure all deferred tasks are completed */ + + (void) acpi_ut_release_mutex (ACPI_MTX_NAMESPACE); + acpi_os_wait_events_complete(NULL); + status = acpi_ut_acquire_mutex (ACPI_MTX_NAMESPACE); + if (ACPI_FAILURE (status)) { + return_ACPI_STATUS (status); + } + /* Remove the handler */ if (handler_type == ACPI_SYSTEM_NOTIFY) { @@ -613,6 +631,15 @@ status = AE_BAD_PARAMETER; goto unlock_and_exit; } + + /* Make sure all deferred tasks are completed */ + + (void) acpi_ut_release_mutex (ACPI_MTX_EVENTS); + acpi_os_wait_events_complete(NULL); + status = acpi_ut_acquire_mutex (ACPI_MTX_EVENTS); + if (ACPI_FAILURE (status)) { + return_ACPI_STATUS (status); + } /* Remove the handler */ diff -Nru a/drivers/acpi/osl.c b/drivers/acpi/osl.c --- a/drivers/acpi/osl.c Sun May 16 01:20:47 2004 +++ b/drivers/acpi/osl.c Sun May 16 01:20:47 2004 @@ -66,6 +66,7 @@ static unsigned int acpi_irq_irq; static OSD_HANDLER acpi_irq_handler; static void *acpi_irq_context; +static struct workqueue_struct *kacpid_wq; acpi_status acpi_os_initialize(void) @@ -80,6 +81,8 @@ return AE_NULL_ENTRY; } #endif + kacpid_wq = create_singlethread_workqueue("kacpid"); + BUG_ON(!kacpid_wq); return AE_OK; } @@ -92,6 +95,8 @@ acpi_irq_handler); } + destroy_workqueue(kacpid_wq); + return AE_OK; } @@ -654,13 +659,20 @@ task = (void *)(dpc+1); INIT_WORK(task, acpi_os_execute_deferred, (void*)dpc); - if (!schedule_work(task)) { - ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Call to schedule_work() failed.\n")); + if (!queue_work(kacpid_wq, task)) { + ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, "Call to queue_work() failed.\n")); kfree(dpc); status = AE_ERROR; } return_ACPI_STATUS (status); +} + +void +acpi_os_wait_events_complete( + void *context) +{ + flush_workqueue(kacpid_wq); } /* diff -Nru a/drivers/acpi/scan.c b/drivers/acpi/scan.c --- a/drivers/acpi/scan.c Sun May 16 01:20:47 2004 +++ b/drivers/acpi/scan.c Sun May 16 01:20:47 2004 @@ -318,8 +318,10 @@ struct acpi_device * dev = container_of(node,struct acpi_device,g_list); if (dev->driver == drv) { + spin_unlock(&acpi_device_lock); if (drv->ops.remove) drv->ops.remove(dev,ACPI_BUS_REMOVAL_NORMAL); + spin_lock(&acpi_device_lock); dev->driver = NULL; dev->driver_data = NULL; atomic_dec(&drv->references); diff -Nru a/drivers/acpi/tables.c b/drivers/acpi/tables.c --- a/drivers/acpi/tables.c Sun May 16 01:20:47 2004 +++ b/drivers/acpi/tables.c Sun May 16 01:20:47 2004 @@ -343,10 +343,11 @@ entry = (acpi_table_entry_header *) ((unsigned long) madt + madt_size); - while (((unsigned long) entry) < madt_end) { + while (((unsigned long) entry) + sizeof(acpi_table_entry_header) < madt_end) { if (entry->type == entry_id && (!max_entries || count++ < max_entries)) - handler(entry); + if (handler(entry, madt_end)) + return -EINVAL; entry = (acpi_table_entry_header *) ((unsigned long) entry + entry->length); diff -Nru a/include/acpi/acpiosxf.h b/include/acpi/acpiosxf.h --- a/include/acpi/acpiosxf.h Sun May 16 01:20:47 2004 +++ b/include/acpi/acpiosxf.h Sun May 16 01:20:47 2004 @@ -213,6 +213,10 @@ void *context); void +acpi_os_wait_events_complete( + void * context); + +void acpi_os_sleep ( u32 seconds, u32 milliseconds); diff -Nru a/include/linux/acpi.h b/include/linux/acpi.h --- a/include/linux/acpi.h Sun May 16 01:20:47 2004 +++ b/include/linux/acpi.h Sun May 16 01:20:47 2004 @@ -374,7 +374,7 @@ extern acpi_table_handler acpi_table_ops[ACPI_TABLE_COUNT]; -typedef int (*acpi_madt_entry_handler) (acpi_table_entry_header *header); +typedef int (*acpi_madt_entry_handler) (acpi_table_entry_header *header, const unsigned long end); char * __acpi_map_table (unsigned long phys_addr, unsigned long size); unsigned long acpi_find_rsdp (void);