From 9e89dde2b063ca73fcdc9244fe68e2dea32c5088 Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Thu, 7 Dec 2006 20:56:16 +0800 Subject: ACPI: clean up scan.c Adjust the code and make code doing similar things together. No logic changes. Signed-off-by : Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 698a154..e0255cb 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -111,233 +111,6 @@ static struct kset acpi_namespace_kset = { .uevent_ops = &namespace_uevent_ops, }; -static void acpi_device_register(struct acpi_device *device, - struct acpi_device *parent) -{ - int err; - - /* - * Linkage - * ------- - * Link this device to its parent and siblings. - */ - INIT_LIST_HEAD(&device->children); - INIT_LIST_HEAD(&device->node); - INIT_LIST_HEAD(&device->g_list); - INIT_LIST_HEAD(&device->wakeup_list); - - spin_lock(&acpi_device_lock); - if (device->parent) { - list_add_tail(&device->node, &device->parent->children); - list_add_tail(&device->g_list, &device->parent->g_list); - } else - list_add_tail(&device->g_list, &acpi_device_list); - if (device->wakeup.flags.valid) - list_add_tail(&device->wakeup_list, &acpi_wakeup_device_list); - spin_unlock(&acpi_device_lock); - - strlcpy(device->kobj.name, device->pnp.bus_id, KOBJ_NAME_LEN); - if (parent) - device->kobj.parent = &parent->kobj; - device->kobj.ktype = &ktype_acpi_ns; - device->kobj.kset = &acpi_namespace_kset; - err = kobject_register(&device->kobj); - if (err < 0) - printk(KERN_WARNING "%s: kobject_register error: %d\n", - __FUNCTION__, err); - create_sysfs_device_files(device); -} - -static void acpi_device_unregister(struct acpi_device *device, int type) -{ - spin_lock(&acpi_device_lock); - if (device->parent) { - list_del(&device->node); - list_del(&device->g_list); - } else - list_del(&device->g_list); - - list_del(&device->wakeup_list); - - spin_unlock(&acpi_device_lock); - - acpi_detach_data(device->handle, acpi_bus_data_handler); - remove_sysfs_device_files(device); - kobject_unregister(&device->kobj); -} - -void acpi_bus_data_handler(acpi_handle handle, u32 function, void *context) -{ - - /* TBD */ - - return; -} - -static int acpi_bus_get_power_flags(struct acpi_device *device) -{ - acpi_status status = 0; - acpi_handle handle = NULL; - u32 i = 0; - - - /* - * Power Management Flags - */ - status = acpi_get_handle(device->handle, "_PSC", &handle); - if (ACPI_SUCCESS(status)) - device->power.flags.explicit_get = 1; - status = acpi_get_handle(device->handle, "_IRC", &handle); - if (ACPI_SUCCESS(status)) - device->power.flags.inrush_current = 1; - - /* - * Enumerate supported power management states - */ - for (i = ACPI_STATE_D0; i <= ACPI_STATE_D3; i++) { - struct acpi_device_power_state *ps = &device->power.states[i]; - char object_name[5] = { '_', 'P', 'R', '0' + i, '\0' }; - - /* Evaluate "_PRx" to se if power resources are referenced */ - acpi_evaluate_reference(device->handle, object_name, NULL, - &ps->resources); - if (ps->resources.count) { - device->power.flags.power_resources = 1; - ps->flags.valid = 1; - } - - /* Evaluate "_PSx" to see if we can do explicit sets */ - object_name[2] = 'S'; - status = acpi_get_handle(device->handle, object_name, &handle); - if (ACPI_SUCCESS(status)) { - ps->flags.explicit_set = 1; - ps->flags.valid = 1; - } - - /* State is valid if we have some power control */ - if (ps->resources.count || ps->flags.explicit_set) - ps->flags.valid = 1; - - ps->power = -1; /* Unknown - driver assigned */ - ps->latency = -1; /* Unknown - driver assigned */ - } - - /* Set defaults for D0 and D3 states (always valid) */ - device->power.states[ACPI_STATE_D0].flags.valid = 1; - device->power.states[ACPI_STATE_D0].power = 100; - device->power.states[ACPI_STATE_D3].flags.valid = 1; - device->power.states[ACPI_STATE_D3].power = 0; - - /* TBD: System wake support and resource requirements. */ - - device->power.state = ACPI_STATE_UNKNOWN; - - return 0; -} - -int acpi_match_ids(struct acpi_device *device, char *ids) -{ - if (device->flags.hardware_id) - if (strstr(ids, device->pnp.hardware_id)) - return 0; - - if (device->flags.compatible_ids) { - struct acpi_compatible_id_list *cid_list = device->pnp.cid_list; - int i; - - /* compare multiple _CID entries against driver ids */ - for (i = 0; i < cid_list->count; i++) { - if (strstr(ids, cid_list->id[i].value)) - return 0; - } - } - return -ENOENT; -} - -static acpi_status -acpi_bus_extract_wakeup_device_power_package(struct acpi_device *device, - union acpi_object *package) -{ - int i = 0; - union acpi_object *element = NULL; - - if (!device || !package || (package->package.count < 2)) - return AE_BAD_PARAMETER; - - element = &(package->package.elements[0]); - if (!element) - return AE_BAD_PARAMETER; - if (element->type == ACPI_TYPE_PACKAGE) { - if ((element->package.count < 2) || - (element->package.elements[0].type != - ACPI_TYPE_LOCAL_REFERENCE) - || (element->package.elements[1].type != ACPI_TYPE_INTEGER)) - return AE_BAD_DATA; - device->wakeup.gpe_device = - element->package.elements[0].reference.handle; - device->wakeup.gpe_number = - (u32) element->package.elements[1].integer.value; - } else if (element->type == ACPI_TYPE_INTEGER) { - device->wakeup.gpe_number = element->integer.value; - } else - return AE_BAD_DATA; - - element = &(package->package.elements[1]); - if (element->type != ACPI_TYPE_INTEGER) { - return AE_BAD_DATA; - } - device->wakeup.sleep_state = element->integer.value; - - if ((package->package.count - 2) > ACPI_MAX_HANDLES) { - return AE_NO_MEMORY; - } - device->wakeup.resources.count = package->package.count - 2; - for (i = 0; i < device->wakeup.resources.count; i++) { - element = &(package->package.elements[i + 2]); - if (element->type != ACPI_TYPE_ANY) { - return AE_BAD_DATA; - } - - device->wakeup.resources.handles[i] = element->reference.handle; - } - - return AE_OK; -} - -static int acpi_bus_get_wakeup_device_flags(struct acpi_device *device) -{ - acpi_status status = 0; - struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; - union acpi_object *package = NULL; - - - /* _PRW */ - status = acpi_evaluate_object(device->handle, "_PRW", NULL, &buffer); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, "Evaluating _PRW")); - goto end; - } - - package = (union acpi_object *)buffer.pointer; - status = acpi_bus_extract_wakeup_device_power_package(device, package); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, "Extracting _PRW package")); - goto end; - } - - kfree(buffer.pointer); - - device->wakeup.flags.valid = 1; - /* Power button, Lid switch always enable wakeup */ - if (!acpi_match_ids(device, "PNP0C0D,PNP0C0C,PNP0C0E")) - device->wakeup.flags.run_wake = 1; - - end: - if (ACPI_FAILURE(status)) - device->flags.wake_capable = 0; - return 0; -} - /* -------------------------------------------------------------------------- ACPI sysfs device file support -------------------------------------------------------------------------- */ @@ -447,20 +220,86 @@ acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) } /* -------------------------------------------------------------------------- - Performance Management + ACPI Bus operations -------------------------------------------------------------------------- */ +static inline struct acpi_device * to_acpi_dev(struct device * dev) +{ + return container_of(dev, struct acpi_device, dev); +} -static int acpi_bus_get_perf_flags(struct acpi_device *device) +static int root_suspend(struct acpi_device * acpi_dev, pm_message_t state) { - device->performance.state = ACPI_STATE_UNKNOWN; + struct acpi_device * dev, * next; + int result; + + spin_lock(&acpi_device_lock); + list_for_each_entry_safe_reverse(dev, next, &acpi_device_list, g_list) { + if (dev->driver && dev->driver->ops.suspend) { + spin_unlock(&acpi_device_lock); + result = dev->driver->ops.suspend(dev, 0); + if (result) { + printk(KERN_ERR PREFIX "[%s - %s] Suspend failed: %d\n", + acpi_device_name(dev), + acpi_device_bid(dev), result); + } + spin_lock(&acpi_device_lock); + } + } + spin_unlock(&acpi_device_lock); return 0; } -/* -------------------------------------------------------------------------- - Driver Management - -------------------------------------------------------------------------- */ +static int acpi_device_suspend(struct device * dev, pm_message_t state) +{ + struct acpi_device * acpi_dev = to_acpi_dev(dev); -static LIST_HEAD(acpi_bus_drivers); + /* + * For now, we should only register 1 generic device - + * the ACPI root device - and from there, we walk the + * tree of ACPI devices to suspend each one using the + * ACPI driver methods. + */ + if (acpi_dev->handle == ACPI_ROOT_OBJECT) + root_suspend(acpi_dev, state); + return 0; +} + +static int root_resume(struct acpi_device * acpi_dev) +{ + struct acpi_device * dev, * next; + int result; + + spin_lock(&acpi_device_lock); + list_for_each_entry_safe(dev, next, &acpi_device_list, g_list) { + if (dev->driver && dev->driver->ops.resume) { + spin_unlock(&acpi_device_lock); + result = dev->driver->ops.resume(dev, 0); + if (result) { + printk(KERN_ERR PREFIX "[%s - %s] resume failed: %d\n", + acpi_device_name(dev), + acpi_device_bid(dev), result); + } + spin_lock(&acpi_device_lock); + } + } + spin_unlock(&acpi_device_lock); + return 0; +} + +static int acpi_device_resume(struct device * dev) +{ + struct acpi_device * acpi_dev = to_acpi_dev(dev); + + /* + * For now, we should only register 1 generic device - + * the ACPI root device - and from there, we walk the + * tree of ACPI devices to resume each one using the + * ACPI driver methods. + */ + if (acpi_dev->handle == ACPI_ROOT_OBJECT) + root_resume(acpi_dev); + return 0; +} /** * acpi_bus_match - match device IDs to driver's supported IDs @@ -478,6 +317,72 @@ acpi_bus_match(struct acpi_device *device, struct acpi_driver *driver) return acpi_match_ids(device, driver->ids); } +static struct bus_type acpi_bus_type = { + .name = "acpi", + .suspend = acpi_device_suspend, + .resume = acpi_device_resume, +}; + +static void acpi_device_register(struct acpi_device *device, + struct acpi_device *parent) +{ + int err; + + /* + * Linkage + * ------- + * Link this device to its parent and siblings. + */ + INIT_LIST_HEAD(&device->children); + INIT_LIST_HEAD(&device->node); + INIT_LIST_HEAD(&device->g_list); + INIT_LIST_HEAD(&device->wakeup_list); + + spin_lock(&acpi_device_lock); + if (device->parent) { + list_add_tail(&device->node, &device->parent->children); + list_add_tail(&device->g_list, &device->parent->g_list); + } else + list_add_tail(&device->g_list, &acpi_device_list); + if (device->wakeup.flags.valid) + list_add_tail(&device->wakeup_list, &acpi_wakeup_device_list); + spin_unlock(&acpi_device_lock); + + strlcpy(device->kobj.name, device->pnp.bus_id, KOBJ_NAME_LEN); + if (parent) + device->kobj.parent = &parent->kobj; + device->kobj.ktype = &ktype_acpi_ns; + device->kobj.kset = &acpi_namespace_kset; + err = kobject_register(&device->kobj); + if (err < 0) + printk(KERN_WARNING "%s: kobject_register error: %d\n", + __FUNCTION__, err); + create_sysfs_device_files(device); +} + +static void acpi_device_unregister(struct acpi_device *device, int type) +{ + spin_lock(&acpi_device_lock); + if (device->parent) { + list_del(&device->node); + list_del(&device->g_list); + } else + list_del(&device->g_list); + + list_del(&device->wakeup_list); + + spin_unlock(&acpi_device_lock); + + acpi_detach_data(device->handle, acpi_bus_data_handler); + remove_sysfs_device_files(device); + kobject_unregister(&device->kobj); +} + +/* -------------------------------------------------------------------------- + Driver Management + -------------------------------------------------------------------------- */ +static LIST_HEAD(acpi_bus_drivers); + /** * acpi_bus_driver_init - add a device to a driver * @device: the device to add and initialize @@ -583,114 +488,290 @@ static void acpi_driver_detach(struct acpi_driver *drv) atomic_dec(&drv->references); } } - spin_unlock(&acpi_device_lock); + spin_unlock(&acpi_device_lock); +} + +/** + * acpi_bus_register_driver - register a driver with the ACPI bus + * @driver: driver being registered + * + * Registers a driver with the ACPI bus. Searches the namespace for all + * devices that match the driver's criteria and binds. Returns zero for + * success or a negative error status for failure. + */ +int acpi_bus_register_driver(struct acpi_driver *driver) +{ + + if (acpi_disabled) + return -ENODEV; + + spin_lock(&acpi_device_lock); + list_add_tail(&driver->node, &acpi_bus_drivers); + spin_unlock(&acpi_device_lock); + acpi_driver_attach(driver); + + return 0; +} + +EXPORT_SYMBOL(acpi_bus_register_driver); + +/** + * acpi_bus_unregister_driver - unregisters a driver with the APIC bus + * @driver: driver to unregister + * + * Unregisters a driver with the ACPI bus. Searches the namespace for all + * devices that match the driver's criteria and unbinds. + */ +void acpi_bus_unregister_driver(struct acpi_driver *driver) +{ + acpi_driver_detach(driver); + + if (!atomic_read(&driver->references)) { + spin_lock(&acpi_device_lock); + list_del_init(&driver->node); + spin_unlock(&acpi_device_lock); + } + return; +} + +EXPORT_SYMBOL(acpi_bus_unregister_driver); + +/** + * acpi_bus_find_driver - check if there is a driver installed for the device + * @device: device that we are trying to find a supporting driver for + * + * Parses the list of registered drivers looking for a driver applicable for + * the specified device. + */ +static int acpi_bus_find_driver(struct acpi_device *device) +{ + int result = 0; + struct list_head *node, *next; + + + spin_lock(&acpi_device_lock); + list_for_each_safe(node, next, &acpi_bus_drivers) { + struct acpi_driver *driver = + container_of(node, struct acpi_driver, node); + + atomic_inc(&driver->references); + spin_unlock(&acpi_device_lock); + if (!acpi_bus_match(device, driver)) { + result = acpi_bus_driver_init(device, driver); + if (!result) + goto Done; + } + atomic_dec(&driver->references); + spin_lock(&acpi_device_lock); + } + spin_unlock(&acpi_device_lock); + + Done: + return result; +} + +/* -------------------------------------------------------------------------- + Device Enumeration + -------------------------------------------------------------------------- */ +acpi_status +acpi_bus_get_ejd(acpi_handle handle, acpi_handle *ejd) +{ + acpi_status status; + acpi_handle tmp; + struct acpi_buffer buffer = {ACPI_ALLOCATE_BUFFER, NULL}; + union acpi_object *obj; + + status = acpi_get_handle(handle, "_EJD", &tmp); + if (ACPI_FAILURE(status)) + return status; + + status = acpi_evaluate_object(handle, "_EJD", NULL, &buffer); + if (ACPI_SUCCESS(status)) { + obj = buffer.pointer; + status = acpi_get_handle(NULL, obj->string.pointer, ejd); + kfree(buffer.pointer); + } + return status; +} +EXPORT_SYMBOL_GPL(acpi_bus_get_ejd); + +void acpi_bus_data_handler(acpi_handle handle, u32 function, void *context) +{ + + /* TBD */ + + return; +} + +int acpi_match_ids(struct acpi_device *device, char *ids) +{ + if (device->flags.hardware_id) + if (strstr(ids, device->pnp.hardware_id)) + return 0; + + if (device->flags.compatible_ids) { + struct acpi_compatible_id_list *cid_list = device->pnp.cid_list; + int i; + + /* compare multiple _CID entries against driver ids */ + for (i = 0; i < cid_list->count; i++) { + if (strstr(ids, cid_list->id[i].value)) + return 0; + } + } + return -ENOENT; +} + +static int acpi_bus_get_perf_flags(struct acpi_device *device) +{ + device->performance.state = ACPI_STATE_UNKNOWN; + return 0; +} + +static acpi_status +acpi_bus_extract_wakeup_device_power_package(struct acpi_device *device, + union acpi_object *package) +{ + int i = 0; + union acpi_object *element = NULL; + + if (!device || !package || (package->package.count < 2)) + return AE_BAD_PARAMETER; + + element = &(package->package.elements[0]); + if (!element) + return AE_BAD_PARAMETER; + if (element->type == ACPI_TYPE_PACKAGE) { + if ((element->package.count < 2) || + (element->package.elements[0].type != + ACPI_TYPE_LOCAL_REFERENCE) + || (element->package.elements[1].type != ACPI_TYPE_INTEGER)) + return AE_BAD_DATA; + device->wakeup.gpe_device = + element->package.elements[0].reference.handle; + device->wakeup.gpe_number = + (u32) element->package.elements[1].integer.value; + } else if (element->type == ACPI_TYPE_INTEGER) { + device->wakeup.gpe_number = element->integer.value; + } else + return AE_BAD_DATA; + + element = &(package->package.elements[1]); + if (element->type != ACPI_TYPE_INTEGER) { + return AE_BAD_DATA; + } + device->wakeup.sleep_state = element->integer.value; + + if ((package->package.count - 2) > ACPI_MAX_HANDLES) { + return AE_NO_MEMORY; + } + device->wakeup.resources.count = package->package.count - 2; + for (i = 0; i < device->wakeup.resources.count; i++) { + element = &(package->package.elements[i + 2]); + if (element->type != ACPI_TYPE_ANY) { + return AE_BAD_DATA; + } + + device->wakeup.resources.handles[i] = element->reference.handle; + } + + return AE_OK; } -/** - * acpi_bus_register_driver - register a driver with the ACPI bus - * @driver: driver being registered - * - * Registers a driver with the ACPI bus. Searches the namespace for all - * devices that match the driver's criteria and binds. Returns zero for - * success or a negative error status for failure. - */ -int acpi_bus_register_driver(struct acpi_driver *driver) +static int acpi_bus_get_wakeup_device_flags(struct acpi_device *device) { + acpi_status status = 0; + struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; + union acpi_object *package = NULL; - if (acpi_disabled) - return -ENODEV; - spin_lock(&acpi_device_lock); - list_add_tail(&driver->node, &acpi_bus_drivers); - spin_unlock(&acpi_device_lock); - acpi_driver_attach(driver); + /* _PRW */ + status = acpi_evaluate_object(device->handle, "_PRW", NULL, &buffer); + if (ACPI_FAILURE(status)) { + ACPI_EXCEPTION((AE_INFO, status, "Evaluating _PRW")); + goto end; + } - return 0; -} + package = (union acpi_object *)buffer.pointer; + status = acpi_bus_extract_wakeup_device_power_package(device, package); + if (ACPI_FAILURE(status)) { + ACPI_EXCEPTION((AE_INFO, status, "Extracting _PRW package")); + goto end; + } -EXPORT_SYMBOL(acpi_bus_register_driver); + kfree(buffer.pointer); -/** - * acpi_bus_unregister_driver - unregisters a driver with the APIC bus - * @driver: driver to unregister - * - * Unregisters a driver with the ACPI bus. Searches the namespace for all - * devices that match the driver's criteria and unbinds. - */ -void acpi_bus_unregister_driver(struct acpi_driver *driver) -{ - acpi_driver_detach(driver); + device->wakeup.flags.valid = 1; + /* Power button, Lid switch always enable wakeup */ + if (!acpi_match_ids(device, "PNP0C0D,PNP0C0C,PNP0C0E")) + device->wakeup.flags.run_wake = 1; - if (!atomic_read(&driver->references)) { - spin_lock(&acpi_device_lock); - list_del_init(&driver->node); - spin_unlock(&acpi_device_lock); - } - return; + end: + if (ACPI_FAILURE(status)) + device->flags.wake_capable = 0; + return 0; } -EXPORT_SYMBOL(acpi_bus_unregister_driver); - -/** - * acpi_bus_find_driver - check if there is a driver installed for the device - * @device: device that we are trying to find a supporting driver for - * - * Parses the list of registered drivers looking for a driver applicable for - * the specified device. - */ -static int acpi_bus_find_driver(struct acpi_device *device) +static int acpi_bus_get_power_flags(struct acpi_device *device) { - int result = 0; - struct list_head *node, *next; + acpi_status status = 0; + acpi_handle handle = NULL; + u32 i = 0; - spin_lock(&acpi_device_lock); - list_for_each_safe(node, next, &acpi_bus_drivers) { - struct acpi_driver *driver = - container_of(node, struct acpi_driver, node); + /* + * Power Management Flags + */ + status = acpi_get_handle(device->handle, "_PSC", &handle); + if (ACPI_SUCCESS(status)) + device->power.flags.explicit_get = 1; + status = acpi_get_handle(device->handle, "_IRC", &handle); + if (ACPI_SUCCESS(status)) + device->power.flags.inrush_current = 1; - atomic_inc(&driver->references); - spin_unlock(&acpi_device_lock); - if (!acpi_bus_match(device, driver)) { - result = acpi_bus_driver_init(device, driver); - if (!result) - goto Done; + /* + * Enumerate supported power management states + */ + for (i = ACPI_STATE_D0; i <= ACPI_STATE_D3; i++) { + struct acpi_device_power_state *ps = &device->power.states[i]; + char object_name[5] = { '_', 'P', 'R', '0' + i, '\0' }; + + /* Evaluate "_PRx" to se if power resources are referenced */ + acpi_evaluate_reference(device->handle, object_name, NULL, + &ps->resources); + if (ps->resources.count) { + device->power.flags.power_resources = 1; + ps->flags.valid = 1; } - atomic_dec(&driver->references); - spin_lock(&acpi_device_lock); - } - spin_unlock(&acpi_device_lock); - Done: - return result; -} + /* Evaluate "_PSx" to see if we can do explicit sets */ + object_name[2] = 'S'; + status = acpi_get_handle(device->handle, object_name, &handle); + if (ACPI_SUCCESS(status)) { + ps->flags.explicit_set = 1; + ps->flags.valid = 1; + } -/* -------------------------------------------------------------------------- - Device Enumeration - -------------------------------------------------------------------------- */ + /* State is valid if we have some power control */ + if (ps->resources.count || ps->flags.explicit_set) + ps->flags.valid = 1; -acpi_status -acpi_bus_get_ejd(acpi_handle handle, acpi_handle *ejd) -{ - acpi_status status; - acpi_handle tmp; - struct acpi_buffer buffer = {ACPI_ALLOCATE_BUFFER, NULL}; - union acpi_object *obj; + ps->power = -1; /* Unknown - driver assigned */ + ps->latency = -1; /* Unknown - driver assigned */ + } - status = acpi_get_handle(handle, "_EJD", &tmp); - if (ACPI_FAILURE(status)) - return status; + /* Set defaults for D0 and D3 states (always valid) */ + device->power.states[ACPI_STATE_D0].flags.valid = 1; + device->power.states[ACPI_STATE_D0].power = 100; + device->power.states[ACPI_STATE_D3].flags.valid = 1; + device->power.states[ACPI_STATE_D3].power = 0; - status = acpi_evaluate_object(handle, "_EJD", NULL, &buffer); - if (ACPI_SUCCESS(status)) { - obj = buffer.pointer; - status = acpi_get_handle(NULL, obj->string.pointer, ejd); - kfree(buffer.pointer); - } - return status; -} -EXPORT_SYMBOL_GPL(acpi_bus_get_ejd); + /* TBD: System wake support and resource requirements. */ + + device->power.state = ACPI_STATE_UNKNOWN; + return 0; +} static int acpi_bus_get_flags(struct acpi_device *device) { @@ -1353,100 +1434,6 @@ static int acpi_bus_scan_fixed(struct acpi_device *root) return result; } - -static inline struct acpi_device * to_acpi_dev(struct device * dev) -{ - return container_of(dev, struct acpi_device, dev); -} - - -static int root_suspend(struct acpi_device * acpi_dev, pm_message_t state) -{ - struct acpi_device * dev, * next; - int result; - - spin_lock(&acpi_device_lock); - list_for_each_entry_safe_reverse(dev, next, &acpi_device_list, g_list) { - if (dev->driver && dev->driver->ops.suspend) { - spin_unlock(&acpi_device_lock); - result = dev->driver->ops.suspend(dev, 0); - if (result) { - printk(KERN_ERR PREFIX "[%s - %s] Suspend failed: %d\n", - acpi_device_name(dev), - acpi_device_bid(dev), result); - } - spin_lock(&acpi_device_lock); - } - } - spin_unlock(&acpi_device_lock); - return 0; -} - - -static int acpi_device_suspend(struct device * dev, pm_message_t state) -{ - struct acpi_device * acpi_dev = to_acpi_dev(dev); - - /* - * For now, we should only register 1 generic device - - * the ACPI root device - and from there, we walk the - * tree of ACPI devices to suspend each one using the - * ACPI driver methods. - */ - if (acpi_dev->handle == ACPI_ROOT_OBJECT) - root_suspend(acpi_dev, state); - return 0; -} - - - -static int root_resume(struct acpi_device * acpi_dev) -{ - struct acpi_device * dev, * next; - int result; - - spin_lock(&acpi_device_lock); - list_for_each_entry_safe(dev, next, &acpi_device_list, g_list) { - if (dev->driver && dev->driver->ops.resume) { - spin_unlock(&acpi_device_lock); - result = dev->driver->ops.resume(dev, 0); - if (result) { - printk(KERN_ERR PREFIX "[%s - %s] resume failed: %d\n", - acpi_device_name(dev), - acpi_device_bid(dev), result); - } - spin_lock(&acpi_device_lock); - } - } - spin_unlock(&acpi_device_lock); - return 0; -} - - -static int acpi_device_resume(struct device * dev) -{ - struct acpi_device * acpi_dev = to_acpi_dev(dev); - - /* - * For now, we should only register 1 generic device - - * the ACPI root device - and from there, we walk the - * tree of ACPI devices to resume each one using the - * ACPI driver methods. - */ - if (acpi_dev->handle == ACPI_ROOT_OBJECT) - root_resume(acpi_dev); - return 0; -} - - -static struct bus_type acpi_bus_type = { - .name = "acpi", - .suspend = acpi_device_suspend, - .resume = acpi_device_resume, -}; - - - static int __init acpi_scan_init(void) { int result; -- cgit v0.10.2 From 1d268b0a0f5407138caf0dec9559d68e657a3a74 Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Thu, 7 Dec 2006 20:56:19 +0800 Subject: ACPI: rename some functions We want the name 'to_acpi_device'. And the current macro 'to_acpi_device' will be removed after device model is setup. So just simply rename them. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index e0255cb..1f75ba6 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -49,13 +49,13 @@ static void setup_sys_fs_device_files(struct acpi_device *dev, #define remove_sysfs_device_files(dev) \ setup_sys_fs_device_files(dev, (acpi_device_sysfs_files *)&sysfs_remove_file) -#define to_acpi_device(n) container_of(n, struct acpi_device, kobj) +#define to_acpi_dev(n) container_of(n, struct acpi_device, kobj) #define to_handle_attr(n) container_of(n, struct acpi_device_attribute, attr); static ssize_t acpi_device_attr_show(struct kobject *kobj, struct attribute *attr, char *buf) { - struct acpi_device *device = to_acpi_device(kobj); + struct acpi_device *device = to_acpi_dev(kobj); struct acpi_device_attribute *attribute = to_handle_attr(attr); return attribute->show ? attribute->show(device, buf) : -EIO; } @@ -63,7 +63,7 @@ static ssize_t acpi_device_attr_store(struct kobject *kobj, struct attribute *attr, const char *buf, size_t len) { - struct acpi_device *device = to_acpi_device(kobj); + struct acpi_device *device = to_acpi_dev(kobj); struct acpi_device_attribute *attribute = to_handle_attr(attr); return attribute->store ? attribute->store(device, buf, len) : -EIO; } @@ -82,7 +82,7 @@ static int namespace_uevent(struct kset *kset, struct kobject *kobj, char **envp, int num_envp, char *buffer, int buffer_size) { - struct acpi_device *dev = to_acpi_device(kobj); + struct acpi_device *dev = to_acpi_dev(kobj); int i = 0; int len = 0; @@ -222,7 +222,7 @@ acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) /* -------------------------------------------------------------------------- ACPI Bus operations -------------------------------------------------------------------------- */ -static inline struct acpi_device * to_acpi_dev(struct device * dev) +static inline struct acpi_device * to_acpi_device(struct device * dev) { return container_of(dev, struct acpi_device, dev); } @@ -251,7 +251,7 @@ static int root_suspend(struct acpi_device * acpi_dev, pm_message_t state) static int acpi_device_suspend(struct device * dev, pm_message_t state) { - struct acpi_device * acpi_dev = to_acpi_dev(dev); + struct acpi_device * acpi_dev = to_acpi_device(dev); /* * For now, we should only register 1 generic device - @@ -288,7 +288,7 @@ static int root_resume(struct acpi_device * acpi_dev) static int acpi_device_resume(struct device * dev) { - struct acpi_device * acpi_dev = to_acpi_dev(dev); + struct acpi_device * acpi_dev = to_acpi_device(dev); /* * For now, we should only register 1 generic device - -- cgit v0.10.2 From d43ec68e9837dfa6618ab473622683fdbf6e68a9 Mon Sep 17 00:00:00 2001 From: Patrick Mochel Date: Thu, 7 Dec 2006 20:56:23 +0800 Subject: ACPI: add device_driver and hepler functions Add device_driver into acpi_driver for driver model. Add helper functions 'to_acpi_device' and 'to_acpi_driver' to get structure acpi_device/acpi_driver by device/device_driver. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 1f75ba6..5b42948 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -222,11 +222,6 @@ acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) /* -------------------------------------------------------------------------- ACPI Bus operations -------------------------------------------------------------------------- */ -static inline struct acpi_device * to_acpi_device(struct device * dev) -{ - return container_of(dev, struct acpi_device, dev); -} - static int root_suspend(struct acpi_device * acpi_dev, pm_message_t state) { struct acpi_device * dev, * next; diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index fdd1095..a09538e 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -136,6 +136,7 @@ struct acpi_driver { atomic_t references; char *ids; /* Supported Hardware IDs */ struct acpi_device_ops ops; + struct device_driver drv; }; /* @@ -301,6 +302,8 @@ struct acpi_device { }; #define acpi_driver_data(d) ((d)->driver_data) +#define to_acpi_device(d) container_of(d, struct acpi_device, dev) +#define to_acpi_driver(d) container_of(d, struct acpi_driver, drv) /* * Events -- cgit v0.10.2 From 5d9464a46918ced087c351a10f38cee95725f85b Mon Sep 17 00:00:00 2001 From: Patrick Mochel Date: Thu, 7 Dec 2006 20:56:27 +0800 Subject: ACPI: add ACPI bus_type for driver model Add ACPI bus_type for Linux driver model. 1. .shutdown method is added into acpi_driver.ops needed by bus_type operations. 2. remove useless parameter 'int state' in .resume method. 3. change parameter 'int state' to 'pm_message_t state' in .suspend method. Note: The new .uevent method mark ACPI drivers by PNPID instead of by name. Udev script needs to look for "HWID=" or "COMPTID=" to load ACPI drivers as a result. Signed-off-by: Li Shaohua Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/battery.c b/drivers/acpi/battery.c index 026e4075..07c3c27 100644 --- a/drivers/acpi/battery.c +++ b/drivers/acpi/battery.c @@ -64,7 +64,7 @@ extern void *acpi_unlock_battery_dir(struct proc_dir_entry *acpi_battery_dir); static int acpi_battery_add(struct acpi_device *device); static int acpi_battery_remove(struct acpi_device *device, int type); -static int acpi_battery_resume(struct acpi_device *device, int status); +static int acpi_battery_resume(struct acpi_device *device); static struct acpi_driver acpi_battery_driver = { .name = ACPI_BATTERY_DRIVER_NAME, @@ -756,7 +756,7 @@ static int acpi_battery_remove(struct acpi_device *device, int type) } /* this is needed to learn about changes made in suspended state */ -static int acpi_battery_resume(struct acpi_device *device, int state) +static int acpi_battery_resume(struct acpi_device *device) { struct acpi_battery *battery; diff --git a/drivers/acpi/fan.c b/drivers/acpi/fan.c index 045c894..b249420 100644 --- a/drivers/acpi/fan.c +++ b/drivers/acpi/fan.c @@ -48,8 +48,8 @@ MODULE_LICENSE("GPL"); static int acpi_fan_add(struct acpi_device *device); static int acpi_fan_remove(struct acpi_device *device, int type); -static int acpi_fan_suspend(struct acpi_device *device, int state); -static int acpi_fan_resume(struct acpi_device *device, int state); +static int acpi_fan_suspend(struct acpi_device *device, pm_message_t state); +static int acpi_fan_resume(struct acpi_device *device); static struct acpi_driver acpi_fan_driver = { .name = ACPI_FAN_DRIVER_NAME, @@ -238,7 +238,7 @@ static int acpi_fan_remove(struct acpi_device *device, int type) return 0; } -static int acpi_fan_suspend(struct acpi_device *device, int state) +static int acpi_fan_suspend(struct acpi_device *device, pm_message_t state) { if (!device) return -EINVAL; @@ -248,7 +248,7 @@ static int acpi_fan_suspend(struct acpi_device *device, int state) return AE_OK; } -static int acpi_fan_resume(struct acpi_device *device, int state) +static int acpi_fan_resume(struct acpi_device *device) { int result = 0; int power_state = 0; diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 5b42948..4647462 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -222,100 +222,124 @@ acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) /* -------------------------------------------------------------------------- ACPI Bus operations -------------------------------------------------------------------------- */ -static int root_suspend(struct acpi_device * acpi_dev, pm_message_t state) +static int acpi_device_suspend(struct device *dev, pm_message_t state) { - struct acpi_device * dev, * next; - int result; + struct acpi_device *acpi_dev = to_acpi_device(dev); + struct acpi_driver *acpi_drv = acpi_dev->driver; - spin_lock(&acpi_device_lock); - list_for_each_entry_safe_reverse(dev, next, &acpi_device_list, g_list) { - if (dev->driver && dev->driver->ops.suspend) { - spin_unlock(&acpi_device_lock); - result = dev->driver->ops.suspend(dev, 0); - if (result) { - printk(KERN_ERR PREFIX "[%s - %s] Suspend failed: %d\n", - acpi_device_name(dev), - acpi_device_bid(dev), result); - } - spin_lock(&acpi_device_lock); - } - } - spin_unlock(&acpi_device_lock); + if (acpi_drv && acpi_drv->ops.suspend) + return acpi_drv->ops.suspend(acpi_dev, state); return 0; } -static int acpi_device_suspend(struct device * dev, pm_message_t state) +static int acpi_device_resume(struct device *dev) { - struct acpi_device * acpi_dev = to_acpi_device(dev); + struct acpi_device *acpi_dev = to_acpi_device(dev); + struct acpi_driver *acpi_drv = acpi_dev->driver; - /* - * For now, we should only register 1 generic device - - * the ACPI root device - and from there, we walk the - * tree of ACPI devices to suspend each one using the - * ACPI driver methods. - */ - if (acpi_dev->handle == ACPI_ROOT_OBJECT) - root_suspend(acpi_dev, state); + if (acpi_drv && acpi_drv->ops.resume) + return acpi_drv->ops.resume(acpi_dev); return 0; } -static int root_resume(struct acpi_device * acpi_dev) +static int acpi_bus_match(struct device *dev, struct device_driver *drv) { - struct acpi_device * dev, * next; - int result; + struct acpi_device *acpi_dev = to_acpi_device(dev); + struct acpi_driver *acpi_drv = to_acpi_driver(drv); - spin_lock(&acpi_device_lock); - list_for_each_entry_safe(dev, next, &acpi_device_list, g_list) { - if (dev->driver && dev->driver->ops.resume) { - spin_unlock(&acpi_device_lock); - result = dev->driver->ops.resume(dev, 0); - if (result) { - printk(KERN_ERR PREFIX "[%s - %s] resume failed: %d\n", - acpi_device_name(dev), - acpi_device_bid(dev), result); - } - spin_lock(&acpi_device_lock); + if (acpi_drv->ops.match) + return !acpi_drv->ops.match(acpi_dev, acpi_drv); + return !acpi_match_ids(acpi_dev, acpi_drv->ids); +} + +static int acpi_device_uevent(struct device *dev, char **envp, int num_envp, + char *buffer, int buffer_size) +{ + struct acpi_device *acpi_dev = to_acpi_device(dev); + int i = 0, length = 0, ret = 0; + + if (acpi_dev->flags.hardware_id) + ret = add_uevent_var(envp, num_envp, &i, + buffer, buffer_size, &length, + "HWID=%s", acpi_dev->pnp.hardware_id); + if (ret) + return -ENOMEM; + if (acpi_dev->flags.compatible_ids) { + int j; + struct acpi_compatible_id_list *cid_list; + + cid_list = acpi_dev->pnp.cid_list; + + for (j = 0; j < cid_list->count; j++) { + ret = add_uevent_var(envp, num_envp, &i, buffer, + buffer_size, &length, "COMPTID=%s", + cid_list->id[j].value); + if (ret) + return -ENOMEM; } } - spin_unlock(&acpi_device_lock); + + envp[i] = NULL; return 0; } -static int acpi_device_resume(struct device * dev) +static int acpi_bus_driver_init(struct acpi_device *, struct acpi_driver *); +static int acpi_start_single_object(struct acpi_device *); +static int acpi_device_probe(struct device * dev) { - struct acpi_device * acpi_dev = to_acpi_device(dev); + struct acpi_device *acpi_dev = to_acpi_device(dev); + struct acpi_driver *acpi_drv = to_acpi_driver(dev->driver); + int ret; + + ret = acpi_bus_driver_init(acpi_dev, acpi_drv); + if (!ret) { + acpi_start_single_object(acpi_dev); + ACPI_DEBUG_PRINT((ACPI_DB_INFO, + "Found driver [%s] for device [%s]\n", + acpi_drv->name, acpi_dev->pnp.bus_id)); + get_device(dev); + } + return ret; +} - /* - * For now, we should only register 1 generic device - - * the ACPI root device - and from there, we walk the - * tree of ACPI devices to resume each one using the - * ACPI driver methods. - */ - if (acpi_dev->handle == ACPI_ROOT_OBJECT) - root_resume(acpi_dev); +static int acpi_device_remove(struct device * dev) +{ + struct acpi_device *acpi_dev = to_acpi_device(dev); + struct acpi_driver *acpi_drv = acpi_dev->driver; + + if (acpi_drv) { + if (acpi_drv->ops.stop) + acpi_drv->ops.stop(acpi_dev, ACPI_BUS_REMOVAL_NORMAL); + if (acpi_drv->ops.remove) + acpi_drv->ops.remove(acpi_dev, ACPI_BUS_REMOVAL_NORMAL); + } + acpi_dev->driver = NULL; + acpi_driver_data(dev) = NULL; + + put_device(dev); return 0; } -/** - * acpi_bus_match - match device IDs to driver's supported IDs - * @device: the device that we are trying to match to a driver - * @driver: driver whose device id table is being checked - * - * Checks the device's hardware (_HID) or compatible (_CID) ids to see if it - * matches the specified driver's criteria. - */ -static int -acpi_bus_match(struct acpi_device *device, struct acpi_driver *driver) +static void acpi_device_shutdown(struct device *dev) { - if (driver && driver->ops.match) - return driver->ops.match(device, driver); - return acpi_match_ids(device, driver->ids); + struct acpi_device *acpi_dev = to_acpi_device(dev); + struct acpi_driver *acpi_drv = acpi_dev->driver; + + if (acpi_drv && acpi_drv->ops.shutdown) + acpi_drv->ops.shutdown(acpi_dev); + + return ; } static struct bus_type acpi_bus_type = { .name = "acpi", .suspend = acpi_device_suspend, .resume = acpi_device_resume, + .shutdown = acpi_device_shutdown, + .match = acpi_bus_match, + .probe = acpi_device_probe, + .remove = acpi_device_remove, + .uevent = acpi_device_uevent, }; static void acpi_device_register(struct acpi_device *device, @@ -449,7 +473,7 @@ static void acpi_driver_attach(struct acpi_driver *drv) continue; spin_unlock(&acpi_device_lock); - if (!acpi_bus_match(dev, drv)) { + if (!acpi_bus_match(&(dev->dev), &(drv->drv))) { if (!acpi_bus_driver_init(dev, drv)) { acpi_start_single_object(dev); atomic_inc(&drv->references); @@ -551,7 +575,7 @@ static int acpi_bus_find_driver(struct acpi_device *device) atomic_inc(&driver->references); spin_unlock(&acpi_device_lock); - if (!acpi_bus_match(device, driver)) { + if (!acpi_bus_match(&(device->dev), &(driver->drv))) { result = acpi_bus_driver_init(device, driver); if (!result) goto Done; diff --git a/drivers/acpi/thermal.c b/drivers/acpi/thermal.c index 5753d06..3650654 100644 --- a/drivers/acpi/thermal.c +++ b/drivers/acpi/thermal.c @@ -82,7 +82,7 @@ MODULE_PARM_DESC(tzp, "Thermal zone polling frequency, in 1/10 seconds.\n"); static int acpi_thermal_add(struct acpi_device *device); static int acpi_thermal_remove(struct acpi_device *device, int type); -static int acpi_thermal_resume(struct acpi_device *device, int state); +static int acpi_thermal_resume(struct acpi_device *device); static int acpi_thermal_state_open_fs(struct inode *inode, struct file *file); static int acpi_thermal_temp_open_fs(struct inode *inode, struct file *file); static int acpi_thermal_trip_open_fs(struct inode *inode, struct file *file); @@ -1356,7 +1356,7 @@ static int acpi_thermal_remove(struct acpi_device *device, int type) return 0; } -static int acpi_thermal_resume(struct acpi_device *device, int state) +static int acpi_thermal_resume(struct acpi_device *device) { struct acpi_thermal *tz = NULL; int i; diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index a09538e..d7dd526 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -92,13 +92,14 @@ typedef int (*acpi_op_remove) (struct acpi_device * device, int type); typedef int (*acpi_op_lock) (struct acpi_device * device, int type); typedef int (*acpi_op_start) (struct acpi_device * device); typedef int (*acpi_op_stop) (struct acpi_device * device, int type); -typedef int (*acpi_op_suspend) (struct acpi_device * device, int state); -typedef int (*acpi_op_resume) (struct acpi_device * device, int state); +typedef int (*acpi_op_suspend) (struct acpi_device * device, pm_message_t state); +typedef int (*acpi_op_resume) (struct acpi_device * device); typedef int (*acpi_op_scan) (struct acpi_device * device); typedef int (*acpi_op_bind) (struct acpi_device * device); typedef int (*acpi_op_unbind) (struct acpi_device * device); typedef int (*acpi_op_match) (struct acpi_device * device, struct acpi_driver * driver); +typedef int (*acpi_op_shutdown) (struct acpi_device * device); struct acpi_bus_ops { u32 acpi_op_add:1; @@ -112,7 +113,8 @@ struct acpi_bus_ops { u32 acpi_op_bind:1; u32 acpi_op_unbind:1; u32 acpi_op_match:1; - u32 reserved:21; + u32 acpi_op_shutdown:1; + u32 reserved:20; }; struct acpi_device_ops { @@ -127,6 +129,7 @@ struct acpi_device_ops { acpi_op_bind bind; acpi_op_unbind unbind; acpi_op_match match; + acpi_op_shutdown shutdown; }; struct acpi_driver { -- cgit v0.10.2 From 1890a97ab3f66d1e99768439f8067608b9b97fe3 Mon Sep 17 00:00:00 2001 From: Patrick Mochel Date: Thu, 7 Dec 2006 20:56:31 +0800 Subject: ACPI: change registration interface to follow driver model ACPI device/driver registration Interfaces are modified to follow Linux driver model. Signed-off-by: Li Shaohua Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 4647462..b616e17 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -25,7 +25,7 @@ DEFINE_SPINLOCK(acpi_device_lock); LIST_HEAD(acpi_wakeup_device_list); -static void acpi_device_release(struct kobject *kobj) +static void acpi_device_release_legacy(struct kobject *kobj) { struct acpi_device *dev = container_of(kobj, struct acpi_device, kobj); kfree(dev->pnp.cid_list); @@ -75,7 +75,7 @@ static struct sysfs_ops acpi_device_sysfs_ops = { static struct kobj_type ktype_acpi_ns = { .sysfs_ops = &acpi_device_sysfs_ops, - .release = acpi_device_release, + .release = acpi_device_release_legacy, }; static int namespace_uevent(struct kset *kset, struct kobject *kobj, @@ -222,6 +222,14 @@ acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) /* -------------------------------------------------------------------------- ACPI Bus operations -------------------------------------------------------------------------- */ +static void acpi_device_release(struct device *dev) +{ + struct acpi_device *acpi_dev = to_acpi_device(dev); + + kfree(acpi_dev->pnp.cid_list); + kfree(acpi_dev); +} + static int acpi_device_suspend(struct device *dev, pm_message_t state) { struct acpi_device *acpi_dev = to_acpi_device(dev); @@ -377,6 +385,14 @@ static void acpi_device_register(struct acpi_device *device, printk(KERN_WARNING "%s: kobject_register error: %d\n", __FUNCTION__, err); create_sysfs_device_files(device); + + if (device->parent) + device->dev.parent = &parent->dev; + device->dev.bus = &acpi_bus_type; + device_initialize(&device->dev); + sprintf(device->dev.bus_id, "%s", device->pnp.bus_id); + device->dev.release = &acpi_device_release; + device_add(&device->dev); } static void acpi_device_unregister(struct acpi_device *device, int type) @@ -395,20 +411,20 @@ static void acpi_device_unregister(struct acpi_device *device, int type) acpi_detach_data(device->handle, acpi_bus_data_handler); remove_sysfs_device_files(device); kobject_unregister(&device->kobj); + + device_unregister(&device->dev); } /* -------------------------------------------------------------------------- Driver Management -------------------------------------------------------------------------- */ -static LIST_HEAD(acpi_bus_drivers); - /** * acpi_bus_driver_init - add a device to a driver * @device: the device to add and initialize * @driver: driver for the device * * Used to initialize a device via its device driver. Called whenever a - * driver is bound to a device. Invokes the driver's add() and start() ops. + * driver is bound to a device. Invokes the driver's add() ops. */ static int acpi_bus_driver_init(struct acpi_device *device, struct acpi_driver *driver) @@ -459,57 +475,6 @@ static int acpi_start_single_object(struct acpi_device *device) return result; } -static void acpi_driver_attach(struct acpi_driver *drv) -{ - struct list_head *node, *next; - - - spin_lock(&acpi_device_lock); - list_for_each_safe(node, next, &acpi_device_list) { - struct acpi_device *dev = - container_of(node, struct acpi_device, g_list); - - if (dev->driver || !dev->status.present) - continue; - spin_unlock(&acpi_device_lock); - - if (!acpi_bus_match(&(dev->dev), &(drv->drv))) { - if (!acpi_bus_driver_init(dev, drv)) { - acpi_start_single_object(dev); - atomic_inc(&drv->references); - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Found driver [%s] for device [%s]\n", - drv->name, dev->pnp.bus_id)); - } - } - spin_lock(&acpi_device_lock); - } - spin_unlock(&acpi_device_lock); -} - -static void acpi_driver_detach(struct acpi_driver *drv) -{ - struct list_head *node, *next; - - - spin_lock(&acpi_device_lock); - list_for_each_safe(node, next, &acpi_device_list) { - 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); - } - } - spin_unlock(&acpi_device_lock); -} - /** * acpi_bus_register_driver - register a driver with the ACPI bus * @driver: driver being registered @@ -520,16 +485,16 @@ static void acpi_driver_detach(struct acpi_driver *drv) */ int acpi_bus_register_driver(struct acpi_driver *driver) { + int ret; if (acpi_disabled) return -ENODEV; + driver->drv.name = driver->name; + driver->drv.bus = &acpi_bus_type; + driver->drv.owner = driver->owner; - spin_lock(&acpi_device_lock); - list_add_tail(&driver->node, &acpi_bus_drivers); - spin_unlock(&acpi_device_lock); - acpi_driver_attach(driver); - - return 0; + ret = driver_register(&driver->drv); + return ret; } EXPORT_SYMBOL(acpi_bus_register_driver); @@ -543,52 +508,11 @@ EXPORT_SYMBOL(acpi_bus_register_driver); */ void acpi_bus_unregister_driver(struct acpi_driver *driver) { - acpi_driver_detach(driver); - - if (!atomic_read(&driver->references)) { - spin_lock(&acpi_device_lock); - list_del_init(&driver->node); - spin_unlock(&acpi_device_lock); - } - return; + driver_unregister(&driver->drv); } EXPORT_SYMBOL(acpi_bus_unregister_driver); -/** - * acpi_bus_find_driver - check if there is a driver installed for the device - * @device: device that we are trying to find a supporting driver for - * - * Parses the list of registered drivers looking for a driver applicable for - * the specified device. - */ -static int acpi_bus_find_driver(struct acpi_device *device) -{ - int result = 0; - struct list_head *node, *next; - - - spin_lock(&acpi_device_lock); - list_for_each_safe(node, next, &acpi_bus_drivers) { - struct acpi_driver *driver = - container_of(node, struct acpi_driver, node); - - atomic_inc(&driver->references); - spin_unlock(&acpi_device_lock); - if (!acpi_bus_match(&(device->dev), &(driver->drv))) { - result = acpi_bus_driver_init(device, driver); - if (!result) - goto Done; - } - atomic_dec(&driver->references); - spin_lock(&acpi_device_lock); - } - spin_unlock(&acpi_device_lock); - - Done: - return result; -} - /* -------------------------------------------------------------------------- Device Enumeration -------------------------------------------------------------------------- */ @@ -1033,32 +957,10 @@ static void acpi_device_get_debug_info(struct acpi_device *device, static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) { - int result = 0; - struct acpi_driver *driver; - - if (!dev) return -EINVAL; - driver = dev->driver; - - if ((driver) && (driver->ops.remove)) { - - if (driver->ops.stop) { - result = driver->ops.stop(dev, ACPI_BUS_REMOVAL_EJECT); - if (result) - return result; - } - - result = dev->driver->ops.remove(dev, ACPI_BUS_REMOVAL_EJECT); - if (result) { - return result; - } - - atomic_dec(&dev->driver->references); - dev->driver = NULL; - acpi_driver_data(dev) = NULL; - } + device_release_driver(&dev->dev); if (!rmdevice) return 0; @@ -1193,17 +1095,6 @@ acpi_add_single_object(struct acpi_device **child, device->parent->ops.bind(device); } - /* - * Locate & Attach Driver - * ---------------------- - * If there's a hardware id (_HID) or compatible ids (_CID) we check - * to see if there's a driver installed for this kind of device. Note - * that drivers can install before or after a device is enumerated. - * - * TBD: Assumes LDM provides driver hot-plug capability. - */ - acpi_bus_find_driver(device); - end: if (!result) *child = device; @@ -1484,14 +1375,6 @@ static int __init acpi_scan_init(void) if (result) goto Done; - acpi_root->dev.bus = &acpi_bus_type; - snprintf(acpi_root->dev.bus_id, BUS_ID_SIZE, "%s", acpi_bus_type.name); - result = device_register(&acpi_root->dev); - if (result) { - /* We don't want to quit even if we failed to add suspend/resume */ - printk(KERN_ERR PREFIX "Could not register device\n"); - } - /* * Enumerate devices in the ACPI namespace. */ diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index d7dd526..807acf6 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -133,13 +133,12 @@ struct acpi_device_ops { }; struct acpi_driver { - struct list_head node; char name[80]; char class[80]; - atomic_t references; char *ids; /* Supported Hardware IDs */ struct acpi_device_ops ops; struct device_driver drv; + struct module *owner; }; /* -- cgit v0.10.2 From a7178df5e7e5730e5daa6cf6d8b8bf73adbe75c0 Mon Sep 17 00:00:00 2001 From: Li Shaohua Date: Thu, 7 Dec 2006 20:56:34 +0800 Subject: ACPI: adjust init order Adjust link order to add ACPI devices to global list before PCI devices. In addition, acpi_bus type must be initialized before any driver loads. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile index bce7ca2..a749510 100644 --- a/drivers/acpi/Makefile +++ b/drivers/acpi/Makefile @@ -37,6 +37,7 @@ endif obj-y += sleep/ obj-y += bus.o glue.o +obj-y += scan.o motherboard.o obj-$(CONFIG_ACPI_AC) += ac.o obj-$(CONFIG_ACPI_BATTERY) += battery.o obj-$(CONFIG_ACPI_BUTTON) += button.o @@ -56,7 +57,6 @@ obj-$(CONFIG_ACPI_NUMA) += numa.o obj-$(CONFIG_ACPI_ASUS) += asus_acpi.o obj-$(CONFIG_ACPI_IBM) += ibm_acpi.o obj-$(CONFIG_ACPI_TOSHIBA) += toshiba_acpi.o -obj-y += scan.o motherboard.o obj-$(CONFIG_ACPI_HOTPLUG_MEMORY) += acpi_memhotplug.o obj-y += cm_sbs.o obj-$(CONFIG_ACPI_SBS) += i2c_ec.o sbs.o -- cgit v0.10.2 From f883d9db008deb20d4969c26475100cec2b7f6f8 Mon Sep 17 00:00:00 2001 From: Patrick Mochel Date: Thu, 7 Dec 2006 20:56:38 +0800 Subject: ACPI: convert to sysfs framework Setup new sysfs framework 1. Remove /sys/firmware/acpi 2. Add ACPI device in device tree. File "eject" for every device that has _EJ0 method is moved from /sys/firmware to /sys/devices. Operation on this file is exactly the same as before. i.e. echo 1 to "eject" will cause hot removal of this device. Corresponding changes should be made in userspace for hot removal. Signed-off-by: Li Shaohua Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c index 279c4ba..da471f6 100644 --- a/drivers/acpi/bus.c +++ b/drivers/acpi/bus.c @@ -195,7 +195,7 @@ int acpi_bus_set_power(acpi_handle handle, int state) if (!device->flags.power_manageable) { ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Device `[%s]' is not power manageable\n", - device->kobj.name)); + device->dev.kobj.name)); return -ENODEV; } /* diff --git a/drivers/acpi/container.c b/drivers/acpi/container.c index 871aa52..914f56a 100644 --- a/drivers/acpi/container.c +++ b/drivers/acpi/container.c @@ -168,7 +168,7 @@ static void container_notify_cb(acpi_handle handle, u32 type, void *context) if (ACPI_FAILURE(status) || !device) { result = container_device_add(&device, handle); if (!result) - kobject_uevent(&device->kobj, + kobject_uevent(&device->dev.kobj, KOBJ_ONLINE); else printk("Failed to add container\n"); @@ -176,13 +176,13 @@ static void container_notify_cb(acpi_handle handle, u32 type, void *context) } else { if (ACPI_SUCCESS(status)) { /* device exist and this is a remove request */ - kobject_uevent(&device->kobj, KOBJ_OFFLINE); + kobject_uevent(&device->dev.kobj, KOBJ_OFFLINE); } } break; case ACPI_NOTIFY_EJECT_REQUEST: if (!acpi_bus_get_device(handle, &device) && device) { - kobject_uevent(&device->kobj, KOBJ_OFFLINE); + kobject_uevent(&device->dev.kobj, KOBJ_OFFLINE); } break; default: diff --git a/drivers/acpi/processor_core.c b/drivers/acpi/processor_core.c index 1908e0d2..46e72c3 100644 --- a/drivers/acpi/processor_core.c +++ b/drivers/acpi/processor_core.c @@ -711,7 +711,7 @@ int acpi_processor_device_add(acpi_handle handle, struct acpi_device **device) return -ENODEV; if ((pr->id >= 0) && (pr->id < NR_CPUS)) { - kobject_uevent(&(*device)->kobj, KOBJ_ONLINE); + kobject_uevent(&(*device)->dev.kobj, KOBJ_ONLINE); } return 0; } @@ -749,13 +749,13 @@ acpi_processor_hotplug_notify(acpi_handle handle, u32 event, void *data) } if (pr->id >= 0 && (pr->id < NR_CPUS)) { - kobject_uevent(&device->kobj, KOBJ_OFFLINE); + kobject_uevent(&device->dev.kobj, KOBJ_OFFLINE); break; } result = acpi_processor_start(device); if ((!result) && ((pr->id >= 0) && (pr->id < NR_CPUS))) { - kobject_uevent(&device->kobj, KOBJ_ONLINE); + kobject_uevent(&device->dev.kobj, KOBJ_ONLINE); } else { printk(KERN_ERR PREFIX "Device [%s] failed to start\n", acpi_device_bid(device)); @@ -778,7 +778,7 @@ acpi_processor_hotplug_notify(acpi_handle handle, u32 event, void *data) } if ((pr->id < NR_CPUS) && (cpu_present(pr->id))) - kobject_uevent(&device->kobj, KOBJ_OFFLINE); + kobject_uevent(&device->dev.kobj, KOBJ_OFFLINE); break; default: ACPI_DEBUG_PRINT((ACPI_DB_INFO, diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index b616e17..97f6bbd 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -24,126 +24,6 @@ static LIST_HEAD(acpi_device_list); DEFINE_SPINLOCK(acpi_device_lock); LIST_HEAD(acpi_wakeup_device_list); - -static void acpi_device_release_legacy(struct kobject *kobj) -{ - struct acpi_device *dev = container_of(kobj, struct acpi_device, kobj); - kfree(dev->pnp.cid_list); - kfree(dev); -} - -struct acpi_device_attribute { - struct attribute attr; - ssize_t(*show) (struct acpi_device *, char *); - ssize_t(*store) (struct acpi_device *, const char *, size_t); -}; - -typedef void acpi_device_sysfs_files(struct kobject *, - const struct attribute *); - -static void setup_sys_fs_device_files(struct acpi_device *dev, - acpi_device_sysfs_files * func); - -#define create_sysfs_device_files(dev) \ - setup_sys_fs_device_files(dev, (acpi_device_sysfs_files *)&sysfs_create_file) -#define remove_sysfs_device_files(dev) \ - setup_sys_fs_device_files(dev, (acpi_device_sysfs_files *)&sysfs_remove_file) - -#define to_acpi_dev(n) container_of(n, struct acpi_device, kobj) -#define to_handle_attr(n) container_of(n, struct acpi_device_attribute, attr); - -static ssize_t acpi_device_attr_show(struct kobject *kobj, - struct attribute *attr, char *buf) -{ - struct acpi_device *device = to_acpi_dev(kobj); - struct acpi_device_attribute *attribute = to_handle_attr(attr); - return attribute->show ? attribute->show(device, buf) : -EIO; -} -static ssize_t acpi_device_attr_store(struct kobject *kobj, - struct attribute *attr, const char *buf, - size_t len) -{ - struct acpi_device *device = to_acpi_dev(kobj); - struct acpi_device_attribute *attribute = to_handle_attr(attr); - return attribute->store ? attribute->store(device, buf, len) : -EIO; -} - -static struct sysfs_ops acpi_device_sysfs_ops = { - .show = acpi_device_attr_show, - .store = acpi_device_attr_store, -}; - -static struct kobj_type ktype_acpi_ns = { - .sysfs_ops = &acpi_device_sysfs_ops, - .release = acpi_device_release_legacy, -}; - -static int namespace_uevent(struct kset *kset, struct kobject *kobj, - char **envp, int num_envp, char *buffer, - int buffer_size) -{ - struct acpi_device *dev = to_acpi_dev(kobj); - int i = 0; - int len = 0; - - if (!dev->driver) - return 0; - - if (add_uevent_var(envp, num_envp, &i, buffer, buffer_size, &len, - "PHYSDEVDRIVER=%s", dev->driver->name)) - return -ENOMEM; - - envp[i] = NULL; - - return 0; -} - -static struct kset_uevent_ops namespace_uevent_ops = { - .uevent = &namespace_uevent, -}; - -static struct kset acpi_namespace_kset = { - .kobj = { - .name = "namespace", - }, - .subsys = &acpi_subsys, - .ktype = &ktype_acpi_ns, - .uevent_ops = &namespace_uevent_ops, -}; - -/* -------------------------------------------------------------------------- - ACPI sysfs device file support - -------------------------------------------------------------------------- */ -static ssize_t acpi_eject_store(struct acpi_device *device, - const char *buf, size_t count); - -#define ACPI_DEVICE_ATTR(_name,_mode,_show,_store) \ -static struct acpi_device_attribute acpi_device_attr_##_name = \ - __ATTR(_name, _mode, _show, _store) - -ACPI_DEVICE_ATTR(eject, 0200, NULL, acpi_eject_store); - -/** - * setup_sys_fs_device_files - sets up the device files under device namespace - * @dev: acpi_device object - * @func: function pointer to create or destroy the device file - */ -static void -setup_sys_fs_device_files(struct acpi_device *dev, - acpi_device_sysfs_files * func) -{ - acpi_status status; - acpi_handle temp = NULL; - - /* - * If device has _EJ0, 'eject' file is created that is used to trigger - * hot-removal function from userland. - */ - status = acpi_get_handle(dev->handle, "_EJ0", &temp); - if (ACPI_SUCCESS(status)) - (*(func)) (&dev->kobj, &acpi_device_attr_eject.attr); -} - static int acpi_eject_operation(acpi_handle handle, int lockable) { struct acpi_object_list arg_list; @@ -180,7 +60,8 @@ static int acpi_eject_operation(acpi_handle handle, int lockable) } static ssize_t -acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) +acpi_eject_store(struct device *d, struct device_attribute *attr, + const char *buf, size_t count) { int result; int ret = count; @@ -188,26 +69,27 @@ acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) acpi_status status; acpi_handle handle; acpi_object_type type = 0; + struct acpi_device *acpi_device = to_acpi_device(d); if ((!count) || (buf[0] != '1')) { return -EINVAL; } #ifndef FORCE_EJECT - if (device->driver == NULL) { + if (acpi_device->driver == NULL) { ret = -ENODEV; goto err; } #endif - status = acpi_get_type(device->handle, &type); - if (ACPI_FAILURE(status) || (!device->flags.ejectable)) { + status = acpi_get_type(acpi_device->handle, &type); + if (ACPI_FAILURE(status) || (!acpi_device->flags.ejectable)) { ret = -ENODEV; goto err; } - islockable = device->flags.lockable; - handle = device->handle; + islockable = acpi_device->flags.lockable; + handle = acpi_device->handle; - result = acpi_bus_trim(device, 1); + result = acpi_bus_trim(acpi_device, 1); if (!result) result = acpi_eject_operation(handle, islockable); @@ -219,6 +101,35 @@ acpi_eject_store(struct acpi_device *device, const char *buf, size_t count) return ret; } +static DEVICE_ATTR(eject, 0200, NULL, acpi_eject_store); + +static void acpi_device_setup_files(struct acpi_device *dev) +{ + acpi_status status; + acpi_handle temp; + + /* + * If device has _EJ0, 'eject' file is created that is used to trigger + * hot-removal function from userland. + */ + status = acpi_get_handle(dev->handle, "_EJ0", &temp); + if (ACPI_SUCCESS(status)) + device_create_file(&dev->dev, &dev_attr_eject); +} + +static void acpi_device_remove_files(struct acpi_device *dev) +{ + acpi_status status; + acpi_handle temp; + + /* + * If device has _EJ0, 'eject' file is created that is used to trigger + * hot-removal function from userland. + */ + status = acpi_get_handle(dev->handle, "_EJ0", &temp); + if (ACPI_SUCCESS(status)) + device_remove_file(&dev->dev, &dev_attr_eject); +} /* -------------------------------------------------------------------------- ACPI Bus operations -------------------------------------------------------------------------- */ @@ -353,8 +264,6 @@ static struct bus_type acpi_bus_type = { static void acpi_device_register(struct acpi_device *device, struct acpi_device *parent) { - int err; - /* * Linkage * ------- @@ -375,17 +284,6 @@ static void acpi_device_register(struct acpi_device *device, list_add_tail(&device->wakeup_list, &acpi_wakeup_device_list); spin_unlock(&acpi_device_lock); - strlcpy(device->kobj.name, device->pnp.bus_id, KOBJ_NAME_LEN); - if (parent) - device->kobj.parent = &parent->kobj; - device->kobj.ktype = &ktype_acpi_ns; - device->kobj.kset = &acpi_namespace_kset; - err = kobject_register(&device->kobj); - if (err < 0) - printk(KERN_WARNING "%s: kobject_register error: %d\n", - __FUNCTION__, err); - create_sysfs_device_files(device); - if (device->parent) device->dev.parent = &parent->dev; device->dev.bus = &acpi_bus_type; @@ -393,6 +291,8 @@ static void acpi_device_register(struct acpi_device *device, sprintf(device->dev.bus_id, "%s", device->pnp.bus_id); device->dev.release = &acpi_device_release; device_add(&device->dev); + + acpi_device_setup_files(device); } static void acpi_device_unregister(struct acpi_device *device, int type) @@ -409,9 +309,8 @@ static void acpi_device_unregister(struct acpi_device *device, int type) spin_unlock(&acpi_device_lock); acpi_detach_data(device->handle, acpi_bus_data_handler); - remove_sysfs_device_files(device); - kobject_unregister(&device->kobj); + acpi_device_remove_files(device); device_unregister(&device->dev); } @@ -1353,10 +1252,6 @@ static int __init acpi_scan_init(void) if (acpi_disabled) return 0; - result = kset_register(&acpi_namespace_kset); - if (result < 0) - printk(KERN_ERR PREFIX "kset_register error: %d\n", result); - result = bus_register(&acpi_bus_type); if (result) { /* We don't want to quit even if we failed to add suspend/resume */ diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index 807acf6..598fab3 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -299,7 +299,6 @@ struct acpi_device { struct acpi_device_ops ops; struct acpi_driver *driver; void *driver_data; - struct kobject kobj; struct device dev; }; -- cgit v0.10.2 From c4168bff32e218b8400cb48b48adb9b7f7bb31b8 Mon Sep 17 00:00:00 2001 From: Li Shaohua Date: Thu, 7 Dec 2006 20:56:41 +0800 Subject: ACPI: add acpi_bus_ops in acpi_device Add acpi_bus_ops in acpi_device to support acpi hot plug. NOTE: Two methods .add and .start in acpi_driver.ops are called separately to probe ACPI devices, while only .probe method is called in driver model. As executing .add and .start separately is critical for ACPI device hot plug, we use acpi_bus_ops to distinguish different code path. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 97f6bbd..2a82645 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -212,7 +212,8 @@ static int acpi_device_probe(struct device * dev) ret = acpi_bus_driver_init(acpi_dev, acpi_drv); if (!ret) { - acpi_start_single_object(acpi_dev); + if (acpi_dev->bus_ops.acpi_op_start) + acpi_start_single_object(acpi_dev); ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Found driver [%s] for device [%s]\n", acpi_drv->name, acpi_dev->pnp.bus_id)); @@ -305,7 +306,6 @@ static void acpi_device_unregister(struct acpi_device *device, int type) list_del(&device->g_list); list_del(&device->wakeup_list); - spin_unlock(&acpi_device_lock); acpi_detach_data(device->handle, acpi_bus_data_handler); @@ -876,7 +876,8 @@ static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) static int acpi_add_single_object(struct acpi_device **child, - struct acpi_device *parent, acpi_handle handle, int type) + struct acpi_device *parent, acpi_handle handle, int type, + struct acpi_bus_ops *ops) { int result = 0; struct acpi_device *device = NULL; @@ -894,6 +895,8 @@ acpi_add_single_object(struct acpi_device **child, device->handle = handle; device->parent = parent; + device->bus_ops = *ops; /* workround for not call .start */ + acpi_device_get_busid(device, handle, type); @@ -1079,14 +1082,14 @@ static int acpi_bus_scan(struct acpi_device *start, struct acpi_bus_ops *ops) if (ops->acpi_op_add) status = acpi_add_single_object(&child, parent, - chandle, type); + chandle, type, ops); else status = acpi_bus_get_device(chandle, &child); if (ACPI_FAILURE(status)) continue; - if (ops->acpi_op_start) { + if (ops->acpi_op_start && !(ops->acpi_op_add)) { status = acpi_start_single_object(child); if (ACPI_FAILURE(status)) continue; @@ -1124,13 +1127,13 @@ acpi_bus_add(struct acpi_device **child, int result; struct acpi_bus_ops ops; + memset(&ops, 0, sizeof(ops)); + ops.acpi_op_add = 1; - result = acpi_add_single_object(child, parent, handle, type); - if (!result) { - memset(&ops, 0, sizeof(ops)); - ops.acpi_op_add = 1; + result = acpi_add_single_object(child, parent, handle, type, &ops); + if (!result) result = acpi_bus_scan(*child, &ops); - } + return result; } @@ -1216,28 +1219,30 @@ static int acpi_bus_scan_fixed(struct acpi_device *root) { int result = 0; struct acpi_device *device = NULL; - + struct acpi_bus_ops ops; if (!root) return -ENODEV; + memset(&ops, 0, sizeof(ops)); + ops.acpi_op_add = 1; + ops.acpi_op_start = 1; + /* * Enumerate all fixed-feature devices. */ if (acpi_fadt.pwr_button == 0) { result = acpi_add_single_object(&device, acpi_root, NULL, - ACPI_BUS_TYPE_POWER_BUTTON); - if (!result) - result = acpi_start_single_object(device); + ACPI_BUS_TYPE_POWER_BUTTON, + &ops); } if (acpi_fadt.sleep_button == 0) { result = acpi_add_single_object(&device, acpi_root, NULL, - ACPI_BUS_TYPE_SLEEP_BUTTON); - if (!result) - result = acpi_start_single_object(device); + ACPI_BUS_TYPE_SLEEP_BUTTON, + &ops); } return result; @@ -1252,6 +1257,10 @@ static int __init acpi_scan_init(void) if (acpi_disabled) return 0; + memset(&ops, 0, sizeof(ops)); + ops.acpi_op_add = 1; + ops.acpi_op_start = 1; + result = bus_register(&acpi_bus_type); if (result) { /* We don't want to quit even if we failed to add suspend/resume */ @@ -1262,11 +1271,7 @@ static int __init acpi_scan_init(void) * Create the root device in the bus's device tree */ result = acpi_add_single_object(&acpi_root, NULL, ACPI_ROOT_OBJECT, - ACPI_BUS_TYPE_SYSTEM); - if (result) - goto Done; - - result = acpi_start_single_object(acpi_root); + ACPI_BUS_TYPE_SYSTEM, &ops); if (result) goto Done; @@ -1274,12 +1279,8 @@ static int __init acpi_scan_init(void) * Enumerate devices in the ACPI namespace. */ result = acpi_bus_scan_fixed(acpi_root); - if (!result) { - memset(&ops, 0, sizeof(ops)); - ops.acpi_op_add = 1; - ops.acpi_op_start = 1; + if (!result) result = acpi_bus_scan(acpi_root, &ops); - } if (result) acpi_device_unregister(acpi_root, ACPI_BUS_REMOVAL_NORMAL); diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index 598fab3..8976dbe 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -300,6 +300,7 @@ struct acpi_device { struct acpi_driver *driver; void *driver_data; struct device dev; + struct acpi_bus_ops bus_ops; /* workaround for different code path for hotplug */ }; #define acpi_driver_data(d) ((d)->driver_data) -- cgit v0.10.2 From 96333578b023957537c3e98b50af7f3b7e08e411 Mon Sep 17 00:00:00 2001 From: Li Shaohua Date: Thu, 7 Dec 2006 20:56:46 +0800 Subject: ACPI: add acpi_bus_removal_type in acpi_device Add removal_type in structure acpi_device for hot removal. ACPI_BUS_REMOVAL_EJECT is used for ACPI device hot removal. Only one parameter is allowed in .remove method due to driver model. So removal_type is added to indicate different removal type. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 2a82645..06b86fa 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -229,9 +229,9 @@ static int acpi_device_remove(struct device * dev) if (acpi_drv) { if (acpi_drv->ops.stop) - acpi_drv->ops.stop(acpi_dev, ACPI_BUS_REMOVAL_NORMAL); + acpi_drv->ops.stop(acpi_dev, acpi_dev->removal_type); if (acpi_drv->ops.remove) - acpi_drv->ops.remove(acpi_dev, ACPI_BUS_REMOVAL_NORMAL); + acpi_drv->ops.remove(acpi_dev, acpi_dev->removal_type); } acpi_dev->driver = NULL; acpi_driver_data(dev) = NULL; @@ -294,6 +294,7 @@ static void acpi_device_register(struct acpi_device *device, device_add(&device->dev); acpi_device_setup_files(device); + device->removal_type = ACPI_BUS_REMOVAL_NORMAL; } static void acpi_device_unregister(struct acpi_device *device, int type) @@ -859,6 +860,7 @@ static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) if (!dev) return -EINVAL; + dev->removal_type = ACPI_BUS_REMOVAL_EJECT; device_release_driver(&dev->dev); if (!rmdevice) diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index 8976dbe..58dc8f6 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -301,6 +301,7 @@ struct acpi_device { void *driver_data; struct device dev; struct acpi_bus_ops bus_ops; /* workaround for different code path for hotplug */ + enum acpi_bus_removal_type removal_type; /* indicate for different removal type */ }; #define acpi_driver_data(d) ((d)->driver_data) -- cgit v0.10.2 From 54a07001b9efb6a3bb9a9d8ac9ddb226e29b5406 Mon Sep 17 00:00:00 2001 From: Li Shaohua Date: Thu, 7 Dec 2006 20:56:51 +0800 Subject: ACPI: consolidate two motherboard drivers into one Consolidate motherboard1 and motherboard2 drivers into one so that driver core doesn't complain that two drivers have the same name. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/motherboard.c b/drivers/acpi/motherboard.c index 2e17ec7..bedb511 100644 --- a/drivers/acpi/motherboard.c +++ b/drivers/acpi/motherboard.c @@ -33,8 +33,7 @@ ACPI_MODULE_NAME("acpi_motherboard") /* Dell use PNP0C01 instead of PNP0C02 */ -#define ACPI_MB_HID1 "PNP0C01" -#define ACPI_MB_HID2 "PNP0C02" +#define ACPI_MB_HID "PNP0C01,PNP0C02" /** * Doesn't care about legacy IO ports, only IO ports beyond 0x1000 are reserved * Doesn't care about the failure of 'request_region', since other may reserve @@ -110,19 +109,10 @@ static int acpi_motherboard_add(struct acpi_device *device) return 0; } -static struct acpi_driver acpi_motherboard_driver1 = { +static struct acpi_driver acpi_motherboard_driver = { .name = "motherboard", .class = "", - .ids = ACPI_MB_HID1, - .ops = { - .add = acpi_motherboard_add, - }, -}; - -static struct acpi_driver acpi_motherboard_driver2 = { - .name = "motherboard", - .class = "", - .ids = ACPI_MB_HID2, + .ids = ACPI_MB_HID, .ops = { .add = acpi_motherboard_add, }, @@ -173,8 +163,7 @@ static void __init acpi_reserve_resources(void) static int __init acpi_motherboard_init(void) { - acpi_bus_register_driver(&acpi_motherboard_driver1); - acpi_bus_register_driver(&acpi_motherboard_driver2); + acpi_bus_register_driver(&acpi_motherboard_driver); /* * Guarantee motherboard IO reservation first * This module must run after scan.c -- cgit v0.10.2 From db3e1cc3257758d8a694d0a6ab29f109fb019853 Mon Sep 17 00:00:00 2001 From: Li Shaohua Date: Thu, 7 Dec 2006 20:57:05 +0800 Subject: ACPI: Convert ACPI PCI .bind/.unbind to use PCI bridge driver acpi_device had a .bind/.unbind methods, but Linux driver model does not. Cut ACPI PCI code over to use the Linux driver model methods. Convert bind/unbind to use a new pci bridge driver. The driver will add/remove _PRT, so we can eventually remove .bind/.unbind methods. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/pci_bind.c b/drivers/acpi/pci_bind.c index 1e2ae6e..d833274 100644 --- a/drivers/acpi/pci_bind.c +++ b/drivers/acpi/pci_bind.c @@ -223,8 +223,6 @@ int acpi_pci_bind(struct acpi_device *device) data->id.segment, data->id.bus, data->id.device, data->id.function)); data->bus = data->dev->subordinate; - device->ops.bind = acpi_pci_bind; - device->ops.unbind = acpi_pci_unbind; } /* @@ -354,8 +352,6 @@ acpi_pci_bind_root(struct acpi_device *device, data->id = *id; data->bus = bus; - device->ops.bind = acpi_pci_bind; - device->ops.unbind = acpi_pci_unbind; acpi_get_name(device->handle, ACPI_FULL_PATHNAME, &buffer); @@ -378,3 +374,55 @@ acpi_pci_bind_root(struct acpi_device *device, return result; } + +#define ACPI_PCI_BRIDGE_DRIVER_NAME "ACPI PCI Bridge Driver" + +static int acpi_pci_bridge_add(struct acpi_device *device); +static int acpi_pci_bridge_remove(struct acpi_device *device, int type); +static int acpi_pci_bridge_match(struct acpi_device *device, + struct acpi_driver *driver); +static struct acpi_driver acpi_pci_bridge_driver = { + .name = ACPI_PCI_BRIDGE_DRIVER_NAME, + .ops = { + .add = acpi_pci_bridge_add, + .remove = acpi_pci_bridge_remove, + .match = acpi_pci_bridge_match, + }, +}; + +static int acpi_pci_bridge_match(struct acpi_device *device, + struct acpi_driver *driver) +{ + acpi_status status; + acpi_handle handle; + + /* pci bridge has _PRT but isn't PNP0A03 */ + status = acpi_get_handle(device->handle, METHOD_NAME__PRT, &handle); + if (ACPI_FAILURE(status)) + return -ENODEV; + if (!acpi_match_ids(device, "PNP0A03")) + return -ENODEV; + return 0; +} + +static int acpi_pci_bridge_add(struct acpi_device *device) +{ + return acpi_pci_bind(device); +} + +static int acpi_pci_bridge_remove(struct acpi_device *device, int type) +{ + return acpi_pci_unbind(device); +} + +static int __init acpi_pci_bridge_init(void) +{ + if (acpi_pci_disabled) + return 0; + if (acpi_bus_register_driver(&acpi_pci_bridge_driver) < 0) + return -ENODEV; + return 0; +} + +/* Should be called after ACPI pci root driver */ +subsys_initcall(acpi_pci_bridge_init); diff --git a/drivers/acpi/pci_root.c b/drivers/acpi/pci_root.c index 0984a1e..9cfc741 100644 --- a/drivers/acpi/pci_root.c +++ b/drivers/acpi/pci_root.c @@ -175,11 +175,6 @@ static int acpi_pci_root_add(struct acpi_device *device) strcpy(acpi_device_class(device), ACPI_PCI_ROOT_CLASS); acpi_driver_data(device) = root; - /* - * TBD: Doesn't the bus driver automatically set this? - */ - device->ops.bind = acpi_pci_bind; - /* * Segment * ------- diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 06b86fa..c566c74 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -866,11 +866,6 @@ static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) if (!rmdevice) return 0; - if (dev->flags.bus_address) { - if ((dev->parent) && (dev->parent->ops.unbind)) - dev->parent->ops.unbind(dev); - } - acpi_device_unregister(dev, ACPI_BUS_REMOVAL_EJECT); return 0; @@ -987,18 +982,6 @@ acpi_add_single_object(struct acpi_device **child, acpi_device_register(device, parent); - /* - * Bind _ADR-Based Devices - * ----------------------- - * If there's a a bus address (_ADR) then we utilize the parent's - * 'bind' function (if exists) to bind the ACPI- and natively- - * enumerated device representations. - */ - if (device->flags.bus_address) { - if (device->parent && device->parent->ops.bind) - device->parent->ops.bind(device); - } - end: if (!result) *child = device; -- cgit v0.10.2 From ae8433324be16673c75951986dcf85f29c090557 Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Thu, 7 Dec 2006 20:57:10 +0800 Subject: ACPI: Set fake hid for non-PNPID ACPI devices We do this mainly because: 1. hid is used to match ACPI devices and drivers. .match method which is incompatible to driver model can be deleted from acpi_driver.ops then. 2. As the .uevent method mark ACPI drivers by PNPID, fake hid is set to non-PNPID devices so that udev script can load the right ACPI driver by looking for "HWID = " or "COMPTID = ". Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/pci_bind.c b/drivers/acpi/pci_bind.c index d833274..aa05e92 100644 --- a/drivers/acpi/pci_bind.c +++ b/drivers/acpi/pci_bind.c @@ -379,32 +379,16 @@ acpi_pci_bind_root(struct acpi_device *device, static int acpi_pci_bridge_add(struct acpi_device *device); static int acpi_pci_bridge_remove(struct acpi_device *device, int type); -static int acpi_pci_bridge_match(struct acpi_device *device, - struct acpi_driver *driver); + static struct acpi_driver acpi_pci_bridge_driver = { .name = ACPI_PCI_BRIDGE_DRIVER_NAME, + .ids = ACPI_PCI_BRIDGE_HID, .ops = { .add = acpi_pci_bridge_add, .remove = acpi_pci_bridge_remove, - .match = acpi_pci_bridge_match, }, }; -static int acpi_pci_bridge_match(struct acpi_device *device, - struct acpi_driver *driver) -{ - acpi_status status; - acpi_handle handle; - - /* pci bridge has _PRT but isn't PNP0A03 */ - status = acpi_get_handle(device->handle, METHOD_NAME__PRT, &handle); - if (ACPI_FAILURE(status)) - return -ENODEV; - if (!acpi_match_ids(device, "PNP0A03")) - return -ENODEV; - return 0; -} - static int acpi_pci_bridge_add(struct acpi_device *device) { return acpi_pci_bind(device); diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index c566c74..9efe3e9 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -166,8 +166,6 @@ static int acpi_bus_match(struct device *dev, struct device_driver *drv) struct acpi_device *acpi_dev = to_acpi_device(dev); struct acpi_driver *acpi_drv = to_acpi_driver(drv); - if (acpi_drv->ops.match) - return !acpi_drv->ops.match(acpi_dev, acpi_drv); return !acpi_match_ids(acpi_dev, acpi_drv->ids); } @@ -706,6 +704,53 @@ static void acpi_device_get_busid(struct acpi_device *device, } } +static int +acpi_video_bus_match(struct acpi_device *device) +{ + acpi_handle h_dummy1; + acpi_handle h_dummy2; + acpi_handle h_dummy3; + + + if (!device) + return -EINVAL; + + /* Since there is no HID, CID for ACPI Video drivers, we have + * to check well known required nodes for each feature we support. + */ + + /* Does this device able to support video switching ? */ + if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOD", &h_dummy1)) && + ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOS", &h_dummy2))) + return 0; + + /* Does this device able to retrieve a video ROM ? */ + if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_ROM", &h_dummy1))) + return 0; + + /* Does this device able to configure which video head to be POSTed ? */ + if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_VPO", &h_dummy1)) && + ACPI_SUCCESS(acpi_get_handle(device->handle, "_GPD", &h_dummy2)) && + ACPI_SUCCESS(acpi_get_handle(device->handle, "_SPD", &h_dummy3))) + return 0; + + return -ENODEV; +} + +static int acpi_pci_bridge_match(struct acpi_device *device) +{ + acpi_status status; + acpi_handle handle; + + /* pci bridge has _PRT but isn't PNP0A03 */ + status = acpi_get_handle(device->handle, METHOD_NAME__PRT, &handle); + if (ACPI_FAILURE(status)) + return -ENODEV; + if (!acpi_match_ids(device, "PNP0A03")) + return -ENODEV; + return 0; +} + static void acpi_device_set_id(struct acpi_device *device, struct acpi_device *parent, acpi_handle handle, int type) @@ -736,6 +781,16 @@ static void acpi_device_set_id(struct acpi_device *device, device->pnp.bus_address = info->address; device->flags.bus_address = 1; } + + if(!(info->valid & (ACPI_VALID_HID | ACPI_VALID_CID))){ + status = acpi_video_bus_match(device); + if(ACPI_SUCCESS(status)) + hid = ACPI_VIDEO_HID; + + status = acpi_pci_bridge_match(device); + if(ACPI_SUCCESS(status)) + hid = ACPI_PCI_BRIDGE_HID; + } break; case ACPI_BUS_TYPE_POWER: hid = ACPI_POWER_HID; diff --git a/drivers/acpi/video.c b/drivers/acpi/video.c index 56666a9..6e99eea 100644 --- a/drivers/acpi/video.c +++ b/drivers/acpi/video.c @@ -65,16 +65,14 @@ MODULE_LICENSE("GPL"); static int acpi_video_bus_add(struct acpi_device *device); static int acpi_video_bus_remove(struct acpi_device *device, int type); -static int acpi_video_bus_match(struct acpi_device *device, - struct acpi_driver *driver); static struct acpi_driver acpi_video_bus = { .name = ACPI_VIDEO_DRIVER_NAME, .class = ACPI_VIDEO_CLASS, + .ids = ACPI_VIDEO_HID, .ops = { .add = acpi_video_bus_add, .remove = acpi_video_bus_remove, - .match = acpi_video_bus_match, }, }; @@ -1774,39 +1772,6 @@ static int acpi_video_bus_remove(struct acpi_device *device, int type) return 0; } -static int -acpi_video_bus_match(struct acpi_device *device, struct acpi_driver *driver) -{ - acpi_handle h_dummy1; - acpi_handle h_dummy2; - acpi_handle h_dummy3; - - - if (!device || !driver) - return -EINVAL; - - /* Since there is no HID, CID for ACPI Video drivers, we have - * to check well known required nodes for each feature we support. - */ - - /* Does this device able to support video switching ? */ - if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOD", &h_dummy1)) && - ACPI_SUCCESS(acpi_get_handle(device->handle, "_DOS", &h_dummy2))) - return 0; - - /* Does this device able to retrieve a video ROM ? */ - if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_ROM", &h_dummy1))) - return 0; - - /* Does this device able to configure which video head to be POSTed ? */ - if (ACPI_SUCCESS(acpi_get_handle(device->handle, "_VPO", &h_dummy1)) && - ACPI_SUCCESS(acpi_get_handle(device->handle, "_GPD", &h_dummy2)) && - ACPI_SUCCESS(acpi_get_handle(device->handle, "_SPD", &h_dummy3))) - return 0; - - return -ENODEV; -} - static int __init acpi_video_init(void) { int result = 0; diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index 58dc8f6..a6b4037 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -97,8 +97,6 @@ typedef int (*acpi_op_resume) (struct acpi_device * device); typedef int (*acpi_op_scan) (struct acpi_device * device); typedef int (*acpi_op_bind) (struct acpi_device * device); typedef int (*acpi_op_unbind) (struct acpi_device * device); -typedef int (*acpi_op_match) (struct acpi_device * device, - struct acpi_driver * driver); typedef int (*acpi_op_shutdown) (struct acpi_device * device); struct acpi_bus_ops { @@ -112,9 +110,8 @@ struct acpi_bus_ops { u32 acpi_op_scan:1; u32 acpi_op_bind:1; u32 acpi_op_unbind:1; - u32 acpi_op_match:1; u32 acpi_op_shutdown:1; - u32 reserved:20; + u32 reserved:21; }; struct acpi_device_ops { @@ -128,7 +125,6 @@ struct acpi_device_ops { acpi_op_scan scan; acpi_op_bind bind; acpi_op_unbind unbind; - acpi_op_match match; acpi_op_shutdown shutdown; }; diff --git a/include/acpi/acpi_drivers.h b/include/acpi/acpi_drivers.h index 6a5bdce..be67750 100644 --- a/include/acpi/acpi_drivers.h +++ b/include/acpi/acpi_drivers.h @@ -43,6 +43,8 @@ #define ACPI_BUTTON_HID_POWERF "ACPI_FPB" #define ACPI_BUTTON_HID_SLEEPF "ACPI_FSB" +#define ACPI_VIDEO_HID "ACPI_VID" +#define ACPI_PCI_BRIDGE_HID "ACPI_PCI" /* -------------------------------------------------------------------------- PCI -------------------------------------------------------------------------- */ -- cgit v0.10.2 From 2dec3ba8d872aa3ffbcdb8f6f8a2c0bcd44e9910 Mon Sep 17 00:00:00 2001 From: Yu Luming Date: Tue, 19 Dec 2006 12:56:17 -0800 Subject: output: Add display output class support Add generic abstract layer for display output switch control. The output sysfs class driver provides an abstract video output layer that can be used to hook platform specific methods to enable/disable video output device through common sysfs interface. Signed-off-by: Luming Yu Cc: "Antonino A. Daplas" Cc: Greg KH Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/drivers/video/output.c b/drivers/video/output.c new file mode 100644 index 0000000..1473f2c --- /dev/null +++ b/drivers/video/output.c @@ -0,0 +1,129 @@ +/* + * output.c - Display Output Switch driver + * + * Copyright (C) 2006 Luming Yu + * + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or (at + * your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + * + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + */ +#include +#include +#include +#include + + +MODULE_DESCRIPTION("Display Output Switcher Lowlevel Control Abstraction"); +MODULE_LICENSE("GPL"); +MODULE_AUTHOR("Luming Yu "); + +static ssize_t video_output_show_state(struct class_device *dev,char *buf) +{ + ssize_t ret_size = 0; + struct output_device *od = to_output_device(dev); + if (od->props) + ret_size = sprintf(buf,"%.8x\n",od->props->get_status(od)); + return ret_size; +} + +static ssize_t video_output_store_state(struct class_device *dev, + const char *buf,size_t count) +{ + char *endp; + struct output_device *od = to_output_device(dev); + int request_state = simple_strtoul(buf,&endp,0); + size_t size = endp - buf; + + if (*endp && isspace(*endp)) + size++; + if (size != count) + return -EINVAL; + + if (od->props) { + od->request_state = request_state; + od->props->set_state(od); + } + return count; +} + +static void video_output_class_release(struct class_device *dev) +{ + struct output_device *od = to_output_device(dev); + kfree(od); +} + +static struct class_device_attribute video_output_attributes[] = { + __ATTR(state, 0644, video_output_show_state, video_output_store_state), + __ATTR_NULL, +}; + +static struct class video_output_class = { + .name = "video_output", + .release = video_output_class_release, + .class_dev_attrs = video_output_attributes, +}; + +struct output_device *video_output_register(const char *name, + struct device *dev, + void *devdata, + struct output_properties *op) +{ + struct output_device *new_dev; + int ret_code = 0; + + new_dev = kzalloc(sizeof(struct output_device),GFP_KERNEL); + if (!new_dev) { + ret_code = -ENOMEM; + goto error_return; + } + new_dev->props = op; + new_dev->class_dev.class = &video_output_class; + new_dev->class_dev.dev = dev; + strlcpy(new_dev->class_dev.class_id,name,KOBJ_NAME_LEN); + class_set_devdata(&new_dev->class_dev,devdata); + ret_code = class_device_register(&new_dev->class_dev); + if (ret_code) { + kfree(new_dev); + goto error_return; + } + return new_dev; + +error_return: + return ERR_PTR(ret_code); +} +EXPORT_SYMBOL(video_output_register); + +void video_output_unregister(struct output_device *dev) +{ + if (!dev) + return; + class_device_unregister(&dev->class_dev); +} +EXPORT_SYMBOL(video_output_unregister); + +static void __exit video_output_class_exit(void) +{ + class_unregister(&video_output_class); +} + +static int __init video_output_class_init(void) +{ + return class_register(&video_output_class); +} + +postcore_initcall(video_output_class_init); +module_exit(video_output_class_exit); diff --git a/include/linux/video_output.h b/include/linux/video_output.h new file mode 100644 index 0000000..e63e0c0 --- /dev/null +++ b/include/linux/video_output.h @@ -0,0 +1,42 @@ +/* + * + * Copyright (C) 2006 Luming Yu + * + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or (at + * your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + * + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + */ +#ifndef _LINUX_VIDEO_OUTPUT_H +#define _LINUX_VIDEO_OUTPUT_H +#include +struct output_device; +struct output_properties { + int (*set_state)(struct output_device *); + int (*get_status)(struct output_device *); +}; +struct output_device { + int request_state; + struct output_properties *props; + struct class_device class_dev; +}; +#define to_output_device(obj) container_of(obj, struct output_device, class_dev) +struct output_device *video_output_register(const char *name, + struct device *dev, + void *devdata, + struct output_properties *op); +void video_output_unregister(struct output_device *dev); +#endif -- cgit v0.10.2 From b03637b8863159a4518cb0a9ab90577460fe3417 Mon Sep 17 00:00:00 2001 From: Yu Luming Date: Tue, 19 Dec 2006 12:56:18 -0800 Subject: output: Add output class document Signed-off-by: Luming Yu Cc: "Antonino A. Daplas" Cc: Greg KH Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/Documentation/video-output.txt b/Documentation/video-output.txt new file mode 100644 index 0000000..e517011 --- /dev/null +++ b/Documentation/video-output.txt @@ -0,0 +1,34 @@ + + Video Output Switcher Control + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + 2006 luming.yu@intel.com + +The output sysfs class driver provides an abstract video output layer that +can be used to hook platform specific methods to enable/disable video output +device through common sysfs interface. For example, on my IBM ThinkPad T42 +laptop, The ACPI video driver registered its output devices and read/write +method for 'state' with output sysfs class. The user interface under sysfs is: + +linux:/sys/class/video_output # tree . +. +|-- CRT0 +| |-- device -> ../../../devices/pci0000:00/0000:00:01.0 +| |-- state +| |-- subsystem -> ../../../class/video_output +| `-- uevent +|-- DVI0 +| |-- device -> ../../../devices/pci0000:00/0000:00:01.0 +| |-- state +| |-- subsystem -> ../../../class/video_output +| `-- uevent +|-- LCD0 +| |-- device -> ../../../devices/pci0000:00/0000:00:01.0 +| |-- state +| |-- subsystem -> ../../../class/video_output +| `-- uevent +`-- TV0 + |-- device -> ../../../devices/pci0000:00/0000:00:01.0 + |-- state + |-- subsystem -> ../../../class/video_output + `-- uevent + -- cgit v0.10.2 From 2f3d000a133f68250635f14f6caf24d32d358090 Mon Sep 17 00:00:00 2001 From: Yu Luming Date: Sat, 11 Nov 2006 02:40:34 +0800 Subject: ACPI: Adds backlight sysfs support for acpi video driver. Adds backlight sysfs support for acpi video driver. signed-off-by: Luming Yu Signed-off-by: Len Brown diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index 6f8c50e..e3f77e2 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -106,7 +106,7 @@ config ACPI_BUTTON config ACPI_VIDEO tristate "Video" - depends on X86 + depends on X86 && BACKLIGHT_CLASS_DEVICE help This driver implement the ACPI Extensions For Display Adapters for integrated graphics devices on motherboard, as specified in diff --git a/drivers/acpi/video.c b/drivers/acpi/video.c index 9200a46..4b09a02 100644 --- a/drivers/acpi/video.c +++ b/drivers/acpi/video.c @@ -32,6 +32,7 @@ #include #include +#include #include #include @@ -56,6 +57,7 @@ #define ACPI_VIDEO_HEAD_INVALID (~0u - 1) #define ACPI_VIDEO_HEAD_END (~0u) +#define MAX_NAME_LEN 20 #define _COMPONENT ACPI_VIDEO_COMPONENT ACPI_MODULE_NAME("acpi_video") @@ -142,11 +144,11 @@ struct acpi_video_device_cap { u8 _ADR:1; /*Return the unique ID */ u8 _BCL:1; /*Query list of brightness control levels supported */ u8 _BCM:1; /*Set the brightness level */ + u8 _BQC:1; /* Get current brightness level */ u8 _DDC:1; /*Return the EDID for this device */ u8 _DCS:1; /*Return status of output device */ u8 _DGS:1; /*Query graphics state */ u8 _DSS:1; /*Device state set */ - u8 _reserved:1; }; struct acpi_video_device_brightness { @@ -163,6 +165,8 @@ struct acpi_video_device { struct acpi_video_bus *video; struct acpi_device *dev; struct acpi_video_device_brightness *brightness; + struct backlight_device *backlight; + struct backlight_properties *data; }; /* bus */ @@ -257,11 +261,35 @@ static void acpi_video_device_bind(struct acpi_video_bus *video, struct acpi_video_device *device); static int acpi_video_device_enumerate(struct acpi_video_bus *video); static int acpi_video_switch_output(struct acpi_video_bus *video, int event); +static int acpi_video_device_lcd_set_level(struct acpi_video_device *device, + int level); +static int acpi_video_device_lcd_get_level_current( + struct acpi_video_device *device, + unsigned long *level); static int acpi_video_get_next_level(struct acpi_video_device *device, u32 level_current, u32 event); static void acpi_video_switch_brightness(struct acpi_video_device *device, int event); +/*backlight device sysfs support*/ +static int acpi_video_get_brightness(struct backlight_device *bd) +{ + unsigned long cur_level; + struct acpi_video_device *vd = + (struct acpi_video_device *)class_get_devdata(&bd->class_dev); + acpi_video_device_lcd_get_level_current(vd, &cur_level); + return (int) cur_level; +} + +static int acpi_video_set_brightness(struct backlight_device *bd) +{ + int request_level = bd->props->brightness; + struct acpi_video_device *vd = + (struct acpi_video_device *)class_get_devdata(&bd->class_dev); + acpi_video_device_lcd_set_level(vd, request_level); + return 0; +} + /* -------------------------------------------------------------------------- Video Management -------------------------------------------------------------------------- */ @@ -499,6 +527,7 @@ static void acpi_video_device_find_cap(struct acpi_video_device *device) acpi_integer status; acpi_handle h_dummy1; int i; + u32 max_level = 0; union acpi_object *obj = NULL; struct acpi_video_device_brightness *br = NULL; @@ -514,6 +543,8 @@ static void acpi_video_device_find_cap(struct acpi_video_device *device) if (ACPI_SUCCESS(acpi_get_handle(device->dev->handle, "_BCM", &h_dummy1))) { device->cap._BCM = 1; } + if (ACPI_SUCCESS(acpi_get_handle(device->dev->handle,"_BQC",&h_dummy1))) + device->cap._BQC = 1; if (ACPI_SUCCESS(acpi_get_handle(device->dev->handle, "_DDC", &h_dummy1))) { device->cap._DDC = 1; } @@ -551,6 +582,8 @@ static void acpi_video_device_find_cap(struct acpi_video_device *device) continue; } br->levels[count] = (u32) o->integer.value; + if (br->levels[count] > max_level) + max_level = br->levels[count]; count++; } out: @@ -569,6 +602,37 @@ static void acpi_video_device_find_cap(struct acpi_video_device *device) kfree(obj); + if (device->cap._BCL && device->cap._BCM && device->cap._BQC){ + unsigned long tmp; + static int count = 0; + char *name; + struct backlight_properties *acpi_video_data; + + name = kzalloc(MAX_NAME_LEN, GFP_KERNEL); + if (!name) + return; + + acpi_video_data = kzalloc( + sizeof(struct backlight_properties), + GFP_KERNEL); + if (!acpi_video_data){ + kfree(name); + return; + } + acpi_video_data->owner = THIS_MODULE; + acpi_video_data->get_brightness = + acpi_video_get_brightness; + acpi_video_data->update_status = + acpi_video_set_brightness; + sprintf(name, "acpi_video%d", count++); + device->data = acpi_video_data; + acpi_video_data->max_brightness = max_level; + acpi_video_device_lcd_get_level_current(device, &tmp); + acpi_video_data->brightness = (int)tmp; + device->backlight = backlight_device_register(name, + NULL, device, acpi_video_data); + kfree(name); + } return; } @@ -1595,7 +1659,10 @@ static int acpi_video_bus_put_one_device(struct acpi_video_device *device) status = acpi_remove_notify_handler(device->dev->handle, ACPI_DEVICE_NOTIFY, acpi_video_device_notify); - + if (device->backlight){ + backlight_device_unregister(device->backlight); + kfree(device->data); + } return 0; } -- cgit v0.10.2 From e49bd2dd5a503bb94fe2f2af45422b610940b75d Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Fri, 8 Dec 2006 17:23:43 +0800 Subject: ACPI: use PNPID:instance_no as bus_id of ACPI device Previously we used the device name in the DSDT, but would crash upon encountering a duplicate. Also, exposing the DSDT device name to the user in a patch isn't a good idea, because it is arbitrary. After some discussion, we finally decided to use "PNPID:instance_no" as the bus_id of ACPI devices. Two attributes for each device are added at the same time, the full pathname in ACPI namespace and hardware_id if it has. NOTE: acpi_bus_id_list is used to keep the information of PNPID and instance number of the given PNPID. Loop the acpi_bus_id_list to find the instance_no of the same PNPID when register a device. If failed, i.e. we don't have a node with this PNPID, allocate one and link it to this list. NOTE: Now I don't take the memory free work in charge. If necessary, I can add a reference count in struct acpi_device_bus_id, and check the reference and when unregister a device, i.e. memory is freed when the reference count of a given PNPID is 0. Signed-off-by: Li Shaohua Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 9efe3e9..769e54b 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -21,9 +21,15 @@ extern struct acpi_device *acpi_root; #define ACPI_BUS_DEVICE_NAME "System Bus" static LIST_HEAD(acpi_device_list); +static LIST_HEAD(acpi_bus_id_list); DEFINE_SPINLOCK(acpi_device_lock); LIST_HEAD(acpi_wakeup_device_list); +struct acpi_device_bus_id{ + char bus_id[9]; + unsigned int instance_no; + struct list_head node; +}; static int acpi_eject_operation(acpi_handle handle, int lockable) { struct acpi_object_list arg_list; @@ -103,18 +109,61 @@ acpi_eject_store(struct device *d, struct device_attribute *attr, static DEVICE_ATTR(eject, 0200, NULL, acpi_eject_store); -static void acpi_device_setup_files(struct acpi_device *dev) +static ssize_t +acpi_device_hid_show(struct device *dev, struct device_attribute *attr, char *buf) { + struct acpi_device *acpi_dev = to_acpi_device(dev); + + return sprintf(buf, "%s\n", acpi_dev->pnp.hardware_id); +} +static DEVICE_ATTR(hid, 0444, acpi_device_hid_show, NULL); + +static ssize_t +acpi_device_path_show(struct device *dev, struct device_attribute *attr, char *buf) { + struct acpi_device *acpi_dev = to_acpi_device(dev); + struct acpi_buffer path = {ACPI_ALLOCATE_BUFFER, NULL}; + int result; + + result = acpi_get_name(acpi_dev->handle, ACPI_FULL_PATHNAME, &path); + if(result) + goto end; + + result = sprintf(buf, "%s\n", (char*)path.pointer); + kfree(path.pointer); + end: + return result; +} +static DEVICE_ATTR(path, 0444, acpi_device_path_show, NULL); + +static int acpi_device_setup_files(struct acpi_device *dev) { acpi_status status; acpi_handle temp; + int result = 0; /* - * If device has _EJ0, 'eject' file is created that is used to trigger - * hot-removal function from userland. + * Devices gotten from FADT don't have a "path" attribute */ + if(dev->handle) { + result = device_create_file(&dev->dev, &dev_attr_path); + if(result) + goto end; + } + + if(dev->flags.hardware_id) { + result = device_create_file(&dev->dev, &dev_attr_hid); + if(result) + goto end; + } + + /* + * If device has _EJ0, 'eject' file is created that is used to trigger + * hot-removal function from userland. + */ status = acpi_get_handle(dev->handle, "_EJ0", &temp); if (ACPI_SUCCESS(status)) - device_create_file(&dev->dev, &dev_attr_eject); + result = device_create_file(&dev->dev, &dev_attr_eject); + end: + return result; } static void acpi_device_remove_files(struct acpi_device *dev) @@ -129,6 +178,11 @@ static void acpi_device_remove_files(struct acpi_device *dev) status = acpi_get_handle(dev->handle, "_EJ0", &temp); if (ACPI_SUCCESS(status)) device_remove_file(&dev->dev, &dev_attr_eject); + + if(dev->flags.hardware_id) + device_remove_file(&dev->dev, &dev_attr_hid); + if(dev->handle) + device_remove_file(&dev->dev, &dev_attr_path); } /* -------------------------------------------------------------------------- ACPI Bus operations @@ -260,9 +314,12 @@ static struct bus_type acpi_bus_type = { .uevent = acpi_device_uevent, }; -static void acpi_device_register(struct acpi_device *device, +static int acpi_device_register(struct acpi_device *device, struct acpi_device *parent) { + int result; + struct acpi_device_bus_id *acpi_device_bus_id, *new_bus_id; + int found = 0; /* * Linkage * ------- @@ -273,7 +330,33 @@ static void acpi_device_register(struct acpi_device *device, INIT_LIST_HEAD(&device->g_list); INIT_LIST_HEAD(&device->wakeup_list); + new_bus_id = kzalloc(sizeof(struct acpi_device_bus_id), GFP_KERNEL); + if (!new_bus_id) { + printk(KERN_ERR PREFIX "Memory allocation error\n"); + return -ENOMEM; + } + spin_lock(&acpi_device_lock); + /* + * Find suitable bus_id and instance number in acpi_bus_id_list + * If failed, create one and link it into acpi_bus_id_list + */ + list_for_each_entry(acpi_device_bus_id, &acpi_bus_id_list, node) { + if(!strcmp(acpi_device_bus_id->bus_id, device->flags.hardware_id? device->pnp.hardware_id : "PNPIDNON")) { + acpi_device_bus_id->instance_no ++; + found = 1; + kfree(new_bus_id); + break; + } + } + if(!found) { + acpi_device_bus_id = new_bus_id; + strcpy(acpi_device_bus_id->bus_id, device->flags.hardware_id ? device->pnp.hardware_id : "PNPIDNON"); + acpi_device_bus_id->instance_no = 0; + list_add_tail(&acpi_device_bus_id->node, &acpi_bus_id_list); + } + sprintf(device->dev.bus_id, "%s:%02x", acpi_device_bus_id->bus_id, acpi_device_bus_id->instance_no); + if (device->parent) { list_add_tail(&device->node, &device->parent->children); list_add_tail(&device->g_list, &device->parent->g_list); @@ -287,12 +370,29 @@ static void acpi_device_register(struct acpi_device *device, device->dev.parent = &parent->dev; device->dev.bus = &acpi_bus_type; device_initialize(&device->dev); - sprintf(device->dev.bus_id, "%s", device->pnp.bus_id); device->dev.release = &acpi_device_release; - device_add(&device->dev); + result = device_add(&device->dev); + if(result) { + printk("Error adding device %s", device->dev.bus_id); + goto end; + } + + result = acpi_device_setup_files(device); + if(result) + ACPI_DEBUG_PRINT((ACPI_DB_ERROR, "Error creating sysfs interface for device %s\n", device->dev.bus_id)); - acpi_device_setup_files(device); device->removal_type = ACPI_BUS_REMOVAL_NORMAL; + return 0; + end: + spin_lock(&acpi_device_lock); + if (device->parent) { + list_del(&device->node); + list_del(&device->g_list); + } else + list_del(&device->g_list); + list_del(&device->wakeup_list); + spin_unlock(&acpi_device_lock); + return result; } static void acpi_device_unregister(struct acpi_device *device, int type) @@ -1035,7 +1135,7 @@ acpi_add_single_object(struct acpi_device **child, acpi_device_get_debug_info(device, handle, type); - acpi_device_register(device, parent); + result = acpi_device_register(device, parent); end: if (!result) -- cgit v0.10.2 From 2786f6e388e9dfe9e7b1c3c6bd7fcfba9cfb9831 Mon Sep 17 00:00:00 2001 From: Rui Zhang Date: Thu, 21 Dec 2006 02:21:13 -0500 Subject: ACPI: fix Supermicro X7DB8+ Boot regression http://bugzilla.kernel.org/show_bug.cgi?id=7695 Originally we converted bind/unbind to use a new pci bridge driver. The driver will add/remove _PRT, so we can eventually remove .bind/.unbind methods. But we found that some of the _ADR-Based devices don't have _PRT, i.e. they are not managed by the new ACPI PCI bridge driver. So that .bind method is not called for some _ADR-Based devices, which leads to a failure. Now we make ACPI PCI Root Bridge Driver scan and binds all _ADR-Based devices once the driver is loaded, in the .add method of ACPI PCI Root Bridge driver. Extra code path for calling .bind/.unbind when _ADR-Based devices are hot added/removed is also added. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/pci_bind.c b/drivers/acpi/pci_bind.c index aa05e92..1e2ae6e 100644 --- a/drivers/acpi/pci_bind.c +++ b/drivers/acpi/pci_bind.c @@ -223,6 +223,8 @@ int acpi_pci_bind(struct acpi_device *device) data->id.segment, data->id.bus, data->id.device, data->id.function)); data->bus = data->dev->subordinate; + device->ops.bind = acpi_pci_bind; + device->ops.unbind = acpi_pci_unbind; } /* @@ -352,6 +354,8 @@ acpi_pci_bind_root(struct acpi_device *device, data->id = *id; data->bus = bus; + device->ops.bind = acpi_pci_bind; + device->ops.unbind = acpi_pci_unbind; acpi_get_name(device->handle, ACPI_FULL_PATHNAME, &buffer); @@ -374,39 +378,3 @@ acpi_pci_bind_root(struct acpi_device *device, return result; } - -#define ACPI_PCI_BRIDGE_DRIVER_NAME "ACPI PCI Bridge Driver" - -static int acpi_pci_bridge_add(struct acpi_device *device); -static int acpi_pci_bridge_remove(struct acpi_device *device, int type); - -static struct acpi_driver acpi_pci_bridge_driver = { - .name = ACPI_PCI_BRIDGE_DRIVER_NAME, - .ids = ACPI_PCI_BRIDGE_HID, - .ops = { - .add = acpi_pci_bridge_add, - .remove = acpi_pci_bridge_remove, - }, -}; - -static int acpi_pci_bridge_add(struct acpi_device *device) -{ - return acpi_pci_bind(device); -} - -static int acpi_pci_bridge_remove(struct acpi_device *device, int type) -{ - return acpi_pci_unbind(device); -} - -static int __init acpi_pci_bridge_init(void) -{ - if (acpi_pci_disabled) - return 0; - if (acpi_bus_register_driver(&acpi_pci_bridge_driver) < 0) - return -ENODEV; - return 0; -} - -/* Should be called after ACPI pci root driver */ -subsys_initcall(acpi_pci_bridge_init); diff --git a/drivers/acpi/pci_root.c b/drivers/acpi/pci_root.c index 9cfc741..2e1a74a 100644 --- a/drivers/acpi/pci_root.c +++ b/drivers/acpi/pci_root.c @@ -151,6 +151,21 @@ static acpi_status try_get_root_bridge_busnr(acpi_handle handle, int *busnum) return AE_OK; } +static void acpi_pci_bridge_scan(struct acpi_device *device) +{ + int status; + struct acpi_device *child = NULL; + + if (device->flags.bus_address) + if (device->parent && device->parent->ops.bind) { + status = device->parent->ops.bind(device); + if (!status) { + list_for_each_entry(child, &device->children, node) + acpi_pci_bridge_scan(child); + } + } +} + static int acpi_pci_root_add(struct acpi_device *device) { int result = 0; @@ -159,6 +174,7 @@ static int acpi_pci_root_add(struct acpi_device *device) acpi_status status = AE_OK; unsigned long value = 0; acpi_handle handle = NULL; + struct acpi_device *child; if (!device) @@ -175,6 +191,8 @@ static int acpi_pci_root_add(struct acpi_device *device) strcpy(acpi_device_class(device), ACPI_PCI_ROOT_CLASS); acpi_driver_data(device) = root; + device->ops.bind = acpi_pci_bind; + /* * Segment * ------- @@ -294,6 +312,12 @@ static int acpi_pci_root_add(struct acpi_device *device) result = acpi_pci_irq_add_prt(device->handle, root->id.segment, root->id.bus); + /* + * Scan and bind all _ADR-Based Devices + */ + list_for_each_entry(child, &device->children, node) + acpi_pci_bridge_scan(child); + end: if (result) { if (!list_empty(&root->node)) diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 769e54b..30a39ba 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -837,20 +837,6 @@ acpi_video_bus_match(struct acpi_device *device) return -ENODEV; } -static int acpi_pci_bridge_match(struct acpi_device *device) -{ - acpi_status status; - acpi_handle handle; - - /* pci bridge has _PRT but isn't PNP0A03 */ - status = acpi_get_handle(device->handle, METHOD_NAME__PRT, &handle); - if (ACPI_FAILURE(status)) - return -ENODEV; - if (!acpi_match_ids(device, "PNP0A03")) - return -ENODEV; - return 0; -} - static void acpi_device_set_id(struct acpi_device *device, struct acpi_device *parent, acpi_handle handle, int type) @@ -886,10 +872,6 @@ static void acpi_device_set_id(struct acpi_device *device, status = acpi_video_bus_match(device); if(ACPI_SUCCESS(status)) hid = ACPI_VIDEO_HID; - - status = acpi_pci_bridge_match(device); - if(ACPI_SUCCESS(status)) - hid = ACPI_PCI_BRIDGE_HID; } break; case ACPI_BUS_TYPE_POWER: @@ -1021,6 +1003,13 @@ static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) if (!rmdevice) return 0; + /* + * unbind _ADR-Based Devices when hot removal + */ + if (dev->flags.bus_address) { + if ((dev->parent) && (dev->parent->ops.unbind)) + dev->parent->ops.unbind(dev); + } acpi_device_unregister(dev, ACPI_BUS_REMOVAL_EJECT); return 0; @@ -1137,6 +1126,14 @@ acpi_add_single_object(struct acpi_device **child, result = acpi_device_register(device, parent); + /* + * Bind _ADR-Based Devices when hot add + */ + if (device->flags.bus_address) { + if (device->parent && device->parent->ops.bind) + device->parent->ops.bind(device); + } + end: if (!result) *child = device; diff --git a/include/acpi/acpi_drivers.h b/include/acpi/acpi_drivers.h index be67750..2781e66 100644 --- a/include/acpi/acpi_drivers.h +++ b/include/acpi/acpi_drivers.h @@ -44,7 +44,6 @@ #define ACPI_BUTTON_HID_SLEEPF "ACPI_FSB" #define ACPI_VIDEO_HID "ACPI_VID" -#define ACPI_PCI_BRIDGE_HID "ACPI_PCI" /* -------------------------------------------------------------------------- PCI -------------------------------------------------------------------------- */ -- cgit v0.10.2 From 82cae99980c158cb9724415547ca59cf95c58792 Mon Sep 17 00:00:00 2001 From: Rui Zhang Date: Wed, 3 Jan 2007 23:40:53 -0500 Subject: ACPI: video: fix LCD monitor seen as CRT http://bugzilla.kernel.org/show_bug.cgi?id=7349 Signed-off-by: Len Brown diff --git a/drivers/acpi/video.c b/drivers/acpi/video.c index 36b37d7..6f760b5 100644 --- a/drivers/acpi/video.c +++ b/drivers/acpi/video.c @@ -57,6 +57,11 @@ #define ACPI_VIDEO_HEAD_INVALID (~0u - 1) #define ACPI_VIDEO_HEAD_END (~0u) +#define ACPI_VIDEO_DISPLAY_CRT 1 +#define ACPI_VIDEO_DISPLAY_TV 2 +#define ACPI_VIDEO_DISPLAY_DVI 3 +#define ACPI_VIDEO_DISPLAY_LCD 4 + #define _COMPONENT ACPI_VIDEO_COMPONENT ACPI_MODULE_NAME("acpi_video") @@ -133,9 +138,10 @@ struct acpi_video_device_flags { u8 crt:1; u8 lcd:1; u8 tvout:1; + u8 dvi:1; u8 bios:1; u8 unknown:1; - u8 reserved:3; + u8 reserved:2; }; struct acpi_video_device_cap { @@ -668,6 +674,8 @@ static int acpi_video_device_info_seq_show(struct seq_file *seq, void *offset) seq_printf(seq, "LCD\n"); else if (dev->flags.tvout) seq_printf(seq, "TVOUT\n"); + else if (dev->flags.dvi) + seq_printf(seq, "DVI\n"); else seq_printf(seq, "UNKNOWN\n"); @@ -1242,6 +1250,16 @@ static int acpi_video_bus_remove_fs(struct acpi_device *device) -------------------------------------------------------------------------- */ /* device interface */ +static struct acpi_video_device_attrib* +acpi_video_get_device_attr(struct acpi_video_bus *video, unsigned long device_id) +{ + int count; + + for(count = 0; count < video->attached_count; count++) + if((video->attached_array[count].value.int_val & 0xffff) == device_id) + return &(video->attached_array[count].value.attrib); + return NULL; +} static int acpi_video_bus_get_one_device(struct acpi_device *device, @@ -1250,7 +1268,7 @@ acpi_video_bus_get_one_device(struct acpi_device *device, unsigned long device_id; int status; struct acpi_video_device *data; - + struct acpi_video_device_attrib* attribute; if (!device || !video) return -EINVAL; @@ -1271,20 +1289,30 @@ acpi_video_bus_get_one_device(struct acpi_device *device, data->video = video; data->dev = device; - switch (device_id & 0xffff) { - case 0x0100: - data->flags.crt = 1; - break; - case 0x0400: - data->flags.lcd = 1; - break; - case 0x0200: - data->flags.tvout = 1; - break; - default: + attribute = acpi_video_get_device_attr(video, device_id); + + if((attribute != NULL) && attribute->device_id_scheme) { + switch (attribute->display_type) { + case ACPI_VIDEO_DISPLAY_CRT: + data->flags.crt = 1; + break; + case ACPI_VIDEO_DISPLAY_TV: + data->flags.tvout = 1; + break; + case ACPI_VIDEO_DISPLAY_DVI: + data->flags.dvi = 1; + break; + case ACPI_VIDEO_DISPLAY_LCD: + data->flags.lcd = 1; + break; + default: + data->flags.unknown = 1; + break; + } + if(attribute->bios_can_detect) + data->flags.bios = 1; + } else data->flags.unknown = 1; - break; - } acpi_video_device_bind(video, data); acpi_video_device_find_cap(data); -- cgit v0.10.2 From bb0958544f3c7c016b2a3025ab3694363e403aa1 Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Thu, 4 Jan 2007 15:03:18 +0800 Subject: ACPI: use more understandable bus_id for ACPI devices Some of the ACPI devices use the internal fake hids which are exposed to userspace as devces' bus_id after sysfs conversion. To make it more friendly, we convert them to more understandable strings. For those devices w/o PNPids, we use "device:instance_no" as the bus_id instead of "PNPIDNON:instance_no". Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 30a39ba..4139e65 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -26,7 +26,7 @@ DEFINE_SPINLOCK(acpi_device_lock); LIST_HEAD(acpi_wakeup_device_list); struct acpi_device_bus_id{ - char bus_id[9]; + char bus_id[15]; unsigned int instance_no; struct list_head node; }; @@ -342,7 +342,7 @@ static int acpi_device_register(struct acpi_device *device, * If failed, create one and link it into acpi_bus_id_list */ list_for_each_entry(acpi_device_bus_id, &acpi_bus_id_list, node) { - if(!strcmp(acpi_device_bus_id->bus_id, device->flags.hardware_id? device->pnp.hardware_id : "PNPIDNON")) { + if(!strcmp(acpi_device_bus_id->bus_id, device->flags.hardware_id? device->pnp.hardware_id : "device")) { acpi_device_bus_id->instance_no ++; found = 1; kfree(new_bus_id); @@ -351,7 +351,7 @@ static int acpi_device_register(struct acpi_device *device, } if(!found) { acpi_device_bus_id = new_bus_id; - strcpy(acpi_device_bus_id->bus_id, device->flags.hardware_id ? device->pnp.hardware_id : "PNPIDNON"); + strcpy(acpi_device_bus_id->bus_id, device->flags.hardware_id ? device->pnp.hardware_id : "device"); acpi_device_bus_id->instance_no = 0; list_add_tail(&acpi_device_bus_id->node, &acpi_bus_id_list); } diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index a6b4037..e7df842 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -184,7 +184,7 @@ struct acpi_device_dir { typedef char acpi_bus_id[5]; typedef unsigned long acpi_bus_address; -typedef char acpi_hardware_id[9]; +typedef char acpi_hardware_id[15]; typedef char acpi_unique_id[9]; typedef char acpi_device_name[40]; typedef char acpi_device_class[20]; diff --git a/include/acpi/acpi_drivers.h b/include/acpi/acpi_drivers.h index 2781e66..1b18c36 100644 --- a/include/acpi/acpi_drivers.h +++ b/include/acpi/acpi_drivers.h @@ -36,14 +36,14 @@ /* _HID definitions */ -#define ACPI_POWER_HID "ACPI_PWR" -#define ACPI_PROCESSOR_HID "ACPI_CPU" -#define ACPI_SYSTEM_HID "ACPI_SYS" -#define ACPI_THERMAL_HID "ACPI_THM" -#define ACPI_BUTTON_HID_POWERF "ACPI_FPB" -#define ACPI_BUTTON_HID_SLEEPF "ACPI_FSB" - -#define ACPI_VIDEO_HID "ACPI_VID" +#define ACPI_POWER_HID "power_resource" +#define ACPI_PROCESSOR_HID "processor" +#define ACPI_SYSTEM_HID "acpi_system" +#define ACPI_THERMAL_HID "thermal" +#define ACPI_BUTTON_HID_POWERF "button_power" +#define ACPI_BUTTON_HID_SLEEPF "button_sleep" +#define ACPI_VIDEO_HID "video" +#define ACPI_BAY_HID "bay" /* -------------------------------------------------------------------------- PCI -------------------------------------------------------------------------- */ -- cgit v0.10.2 From d91a0078476ca536d76419f3b53196873b2931bc Mon Sep 17 00:00:00 2001 From: Justin Chen Date: Wed, 6 Dec 2006 10:17:10 -0700 Subject: ACPI: Optimize acpi_get_pci_rootbridge_handle() to boot faster Move acpi_get_pci_rootbridge_handle() from glue.c to pci_root.c and get the root bridge ACPI handles by searching the &acpi_pci_roots list instead of walking through the ACPI name space. This significantly reduces boot time on large I/O systems. Signed-off-by: Justin Chen Signed-off-by: Bjorn Helgaas Signed-off-by: Len Brown diff --git a/drivers/acpi/glue.c b/drivers/acpi/glue.c index 8a0324b..7b6c9ff 100644 --- a/drivers/acpi/glue.c +++ b/drivers/acpi/glue.c @@ -86,129 +86,6 @@ static int acpi_find_bridge_device(struct device *dev, acpi_handle * handle) return ret; } -/* Get PCI root bridge's handle from its segment and bus number */ -struct acpi_find_pci_root { - unsigned int seg; - unsigned int bus; - acpi_handle handle; -}; - -static acpi_status -do_root_bridge_busnr_callback(struct acpi_resource *resource, void *data) -{ - unsigned long *busnr = data; - struct acpi_resource_address64 address; - - if (resource->type != ACPI_RESOURCE_TYPE_ADDRESS16 && - resource->type != ACPI_RESOURCE_TYPE_ADDRESS32 && - resource->type != ACPI_RESOURCE_TYPE_ADDRESS64) - return AE_OK; - - acpi_resource_to_address64(resource, &address); - if ((address.address_length > 0) && - (address.resource_type == ACPI_BUS_NUMBER_RANGE)) - *busnr = address.minimum; - - return AE_OK; -} - -static int get_root_bridge_busnr(acpi_handle handle) -{ - acpi_status status; - unsigned long bus, bbn; - struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; - - acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); - - status = acpi_evaluate_integer(handle, METHOD_NAME__BBN, NULL, - &bbn); - if (status == AE_NOT_FOUND) { - /* Assume bus = 0 */ - printk(KERN_INFO PREFIX - "Assume root bridge [%s] bus is 0\n", - (char *)buffer.pointer); - status = AE_OK; - bbn = 0; - } - if (ACPI_FAILURE(status)) { - bbn = -ENODEV; - goto exit; - } - if (bbn > 0) - goto exit; - - /* _BBN in some systems return 0 for all root bridges */ - bus = -1; - status = acpi_walk_resources(handle, METHOD_NAME__CRS, - do_root_bridge_busnr_callback, &bus); - /* If _CRS failed, we just use _BBN */ - if (ACPI_FAILURE(status) || (bus == -1)) - goto exit; - /* We select _CRS */ - if (bbn != bus) { - printk(KERN_INFO PREFIX - "_BBN and _CRS returns different value for %s. Select _CRS\n", - (char *)buffer.pointer); - bbn = bus; - } - exit: - kfree(buffer.pointer); - return (int)bbn; -} - -static acpi_status -find_pci_rootbridge(acpi_handle handle, u32 lvl, void *context, void **rv) -{ - struct acpi_find_pci_root *find = (struct acpi_find_pci_root *)context; - unsigned long seg, bus; - acpi_status status; - int tmp; - struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; - - acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); - - status = acpi_evaluate_integer(handle, METHOD_NAME__SEG, NULL, &seg); - if (status == AE_NOT_FOUND) { - /* Assume seg = 0 */ - status = AE_OK; - seg = 0; - } - if (ACPI_FAILURE(status)) { - status = AE_CTRL_DEPTH; - goto exit; - } - - tmp = get_root_bridge_busnr(handle); - if (tmp < 0) { - printk(KERN_ERR PREFIX - "Find root bridge failed for %s\n", - (char *)buffer.pointer); - status = AE_CTRL_DEPTH; - goto exit; - } - bus = tmp; - - if (seg == find->seg && bus == find->bus) - { - find->handle = handle; - status = AE_CTRL_TERMINATE; - } - else - status = AE_OK; - exit: - kfree(buffer.pointer); - return status; -} - -acpi_handle acpi_get_pci_rootbridge_handle(unsigned int seg, unsigned int bus) -{ - struct acpi_find_pci_root find = { seg, bus, NULL }; - - acpi_get_devices(PCI_ROOT_HID_STRING, find_pci_rootbridge, &find, NULL); - return find.handle; -} -EXPORT_SYMBOL_GPL(acpi_get_pci_rootbridge_handle); - /* Get device's handler per its address under its parent */ struct acpi_find_child { acpi_handle handle; diff --git a/drivers/acpi/pci_root.c b/drivers/acpi/pci_root.c index a860efa..1f06229 100644 --- a/drivers/acpi/pci_root.c +++ b/drivers/acpi/pci_root.c @@ -117,6 +117,19 @@ void acpi_pci_unregister_driver(struct acpi_pci_driver *driver) EXPORT_SYMBOL(acpi_pci_unregister_driver); +acpi_handle acpi_get_pci_rootbridge_handle(unsigned int seg, unsigned int bus) +{ + struct acpi_pci_root *tmp; + + list_for_each_entry(tmp, &acpi_pci_roots, node) { + if ((tmp->id.segment == (u16) seg) && (tmp->id.bus == (u16) bus)) + return tmp->device->handle; + } + return NULL; +} + +EXPORT_SYMBOL_GPL(acpi_get_pci_rootbridge_handle); + static acpi_status get_root_bridge_busnr_callback(struct acpi_resource *resource, void *data) { -- cgit v0.10.2 From 9a47cdb1bb85e7944fb7419e4078c46516ef7335 Mon Sep 17 00:00:00 2001 From: Bjorn Helgaas Date: Thu, 18 Jan 2007 16:42:55 -0700 Subject: ACPI: move FADT resource reservations from motherboard driver to osl Resources described by the FADT aren't really a good fit for the ACPI motherboard driver. The motherboard driver cares about PNP0C01 and PNP0C02 devices and their resources. The FADT describes some resources used by the ACPI core. Often, they are also described by by the _CRS of a motherboard device, but I think it's better to reserve them specifically in the ACPI osl.c because (a) the motherboard driver is optional and ACPI uses the resources even if the driver is absent, and (b) I want to remove the ACPI motherboard driver because it's mostly redundant with the PNP system.c driver. Signed-off-by: Bjorn Helgaas Signed-off-by: Len Brown diff --git a/drivers/acpi/motherboard.c b/drivers/acpi/motherboard.c index bedb511..cddab7b 100644 --- a/drivers/acpi/motherboard.c +++ b/drivers/acpi/motherboard.c @@ -118,58 +118,9 @@ static struct acpi_driver acpi_motherboard_driver = { }, }; -static void __init acpi_request_region (struct acpi_generic_address *addr, - unsigned int length, char *desc) -{ - if (!addr->address || !length) - return; - - if (addr->address_space_id == ACPI_ADR_SPACE_SYSTEM_IO) - request_region(addr->address, length, desc); - else if (addr->address_space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) - request_mem_region(addr->address, length, desc); -} - -static void __init acpi_reserve_resources(void) -{ - acpi_request_region(&acpi_gbl_FADT->xpm1a_evt_blk, - acpi_gbl_FADT->pm1_evt_len, "ACPI PM1a_EVT_BLK"); - - acpi_request_region(&acpi_gbl_FADT->xpm1b_evt_blk, - acpi_gbl_FADT->pm1_evt_len, "ACPI PM1b_EVT_BLK"); - - acpi_request_region(&acpi_gbl_FADT->xpm1a_cnt_blk, - acpi_gbl_FADT->pm1_cnt_len, "ACPI PM1a_CNT_BLK"); - - acpi_request_region(&acpi_gbl_FADT->xpm1b_cnt_blk, - acpi_gbl_FADT->pm1_cnt_len, "ACPI PM1b_CNT_BLK"); - - if (acpi_gbl_FADT->pm_tm_len == 4) - acpi_request_region(&acpi_gbl_FADT->xpm_tmr_blk, 4, "ACPI PM_TMR"); - - acpi_request_region(&acpi_gbl_FADT->xpm2_cnt_blk, - acpi_gbl_FADT->pm2_cnt_len, "ACPI PM2_CNT_BLK"); - - /* Length of GPE blocks must be a non-negative multiple of 2 */ - - if (!(acpi_gbl_FADT->gpe0_blk_len & 0x1)) - acpi_request_region(&acpi_gbl_FADT->xgpe0_blk, - acpi_gbl_FADT->gpe0_blk_len, "ACPI GPE0_BLK"); - - if (!(acpi_gbl_FADT->gpe1_blk_len & 0x1)) - acpi_request_region(&acpi_gbl_FADT->xgpe1_blk, - acpi_gbl_FADT->gpe1_blk_len, "ACPI GPE1_BLK"); -} - static int __init acpi_motherboard_init(void) { acpi_bus_register_driver(&acpi_motherboard_driver); - /* - * Guarantee motherboard IO reservation first - * This module must run after scan.c - */ - if (!acpi_disabled) - acpi_reserve_resources(); return 0; } diff --git a/drivers/acpi/osl.c b/drivers/acpi/osl.c index 02b30ae..0acd0e7 100644 --- a/drivers/acpi/osl.c +++ b/drivers/acpi/osl.c @@ -75,6 +75,54 @@ static acpi_osd_handler acpi_irq_handler; static void *acpi_irq_context; static struct workqueue_struct *kacpid_wq; +static void __init acpi_request_region (struct acpi_generic_address *addr, + unsigned int length, char *desc) +{ + struct resource *res; + + if (!addr->address || !length) + return; + + if (addr->address_space_id == ACPI_ADR_SPACE_SYSTEM_IO) + res = request_region(addr->address, length, desc); + else if (addr->address_space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) + res = request_mem_region(addr->address, length, desc); +} + +static int __init acpi_reserve_resources(void) +{ + acpi_request_region(&acpi_fadt.xpm1a_evt_blk, acpi_fadt.pm1_evt_len, + "ACPI PM1a_EVT_BLK"); + + acpi_request_region(&acpi_fadt.xpm1b_evt_blk, acpi_fadt.pm1_evt_len, + "ACPI PM1b_EVT_BLK"); + + acpi_request_region(&acpi_fadt.xpm1a_cnt_blk, acpi_fadt.pm1_cnt_len, + "ACPI PM1a_CNT_BLK"); + + acpi_request_region(&acpi_fadt.xpm1b_cnt_blk, acpi_fadt.pm1_cnt_len, + "ACPI PM1b_CNT_BLK"); + + if (acpi_fadt.pm_tm_len == 4) + acpi_request_region(&acpi_fadt.xpm_tmr_blk, 4, "ACPI PM_TMR"); + + acpi_request_region(&acpi_fadt.xpm2_cnt_blk, acpi_fadt.pm2_cnt_len, + "ACPI PM2_CNT_BLK"); + + /* Length of GPE blocks must be a non-negative multiple of 2 */ + + if (!(acpi_fadt.gpe0_blk_len & 0x1)) + acpi_request_region(&acpi_fadt.xgpe0_blk, + acpi_fadt.gpe0_blk_len, "ACPI GPE0_BLK"); + + if (!(acpi_fadt.gpe1_blk_len & 0x1)) + acpi_request_region(&acpi_fadt.xgpe1_blk, + acpi_fadt.gpe1_blk_len, "ACPI GPE1_BLK"); + + return 0; +} +device_initcall(acpi_reserve_resources); + acpi_status acpi_os_initialize(void) { return AE_OK; -- cgit v0.10.2 From a8c78f7fb1571764f48b8af5459abdd2c66a765f Mon Sep 17 00:00:00 2001 From: Bjorn Helgaas Date: Thu, 18 Jan 2007 16:43:27 -0700 Subject: PNP: reserve system board iomem resources as well as ioport resources Most x86 boxes have no iomem system board resources, but some ia64 boxes do. Signed-off-by: Bjorn Helgaas Signed-off-by: Len Brown diff --git a/drivers/pnp/system.c b/drivers/pnp/system.c index d42015c..fd17c71 100644 --- a/drivers/pnp/system.c +++ b/drivers/pnp/system.c @@ -3,7 +3,8 @@ * * Some code is based on pnpbios_core.c * Copyright 2002 Adam Belay - * + * (c) Copyright 2007 Hewlett-Packard Development Company, L.P. + * Bjorn Helgaas */ #include @@ -21,7 +22,7 @@ static const struct pnp_device_id pnp_dev_table[] = { { "", 0 } }; -static void reserve_ioport_range(char *pnpid, int start, int end) +static void reserve_range(char *pnpid, int start, int end, int port) { struct resource *res; char *regionid; @@ -30,7 +31,10 @@ static void reserve_ioport_range(char *pnpid, int start, int end) if ( regionid == NULL ) return; snprintf(regionid, 16, "pnp %s", pnpid); - res = request_region(start,end-start+1,regionid); + if (port) + res = request_region(start,end-start+1,regionid); + else + res = request_mem_region(start,end-start+1,regionid); if ( res == NULL ) kfree( regionid ); else @@ -41,8 +45,8 @@ static void reserve_ioport_range(char *pnpid, int start, int end) * have double reservations. */ printk(KERN_INFO - "pnp: %s: ioport range 0x%x-0x%x %s reserved\n", - pnpid, start, end, + "pnp: %s: %s range 0x%x-0x%x %s reserved\n", + pnpid, port ? "ioport" : "iomem", start, end, NULL != res ? "has been" : "could not be" ); @@ -75,13 +79,21 @@ static void reserve_resources_of_dev( struct pnp_dev *dev ) /* invalid endpoint */ /* Do nothing */ continue; - reserve_ioport_range( + reserve_range( dev->dev.bus_id, pnp_port_start(dev, i), - pnp_port_end(dev, i) + pnp_port_end(dev, i), 1 ); } + for (i = 0; i < PNP_MAX_MEM; i++) { + if (!pnp_mem_valid(dev, i)) + continue; + + reserve_range(dev->dev.bus_id, pnp_mem_start(dev, i), + pnp_mem_end(dev, i), 0); + } + return; } -- cgit v0.10.2 From 5859554c3ad31b722f0b5a1d3a40e19d8ccedd0b Mon Sep 17 00:00:00 2001 From: Bjorn Helgaas Date: Thu, 18 Jan 2007 16:43:46 -0700 Subject: PNP: system.c whitespace cleanup No functional change. Signed-off-by: Bjorn Helgaas Signed-off-by: Len Brown diff --git a/drivers/pnp/system.c b/drivers/pnp/system.c index fd17c71..2065e74 100644 --- a/drivers/pnp/system.c +++ b/drivers/pnp/system.c @@ -28,15 +28,15 @@ static void reserve_range(char *pnpid, int start, int end, int port) char *regionid; regionid = kmalloc(16, GFP_KERNEL); - if ( regionid == NULL ) + if (regionid == NULL) return; snprintf(regionid, 16, "pnp %s", pnpid); if (port) res = request_region(start,end-start+1,regionid); else res = request_mem_region(start,end-start+1,regionid); - if ( res == NULL ) - kfree( regionid ); + if (res == NULL) + kfree(regionid); else res->flags &= ~IORESOURCE_BUSY; /* @@ -47,24 +47,18 @@ static void reserve_range(char *pnpid, int start, int end, int port) printk(KERN_INFO "pnp: %s: %s range 0x%x-0x%x %s reserved\n", pnpid, port ? "ioport" : "iomem", start, end, - NULL != res ? "has been" : "could not be" - ); - - return; + NULL != res ? "has been" : "could not be"); } -static void reserve_resources_of_dev( struct pnp_dev *dev ) +static void reserve_resources_of_dev(struct pnp_dev *dev) { int i; - for (i=0;idev.bus_id, - pnp_port_start(dev, i), - pnp_port_end(dev, i), 1 - ); + continue; /* invalid */ + + reserve_range(dev->dev.bus_id, pnp_port_start(dev, i), + pnp_port_end(dev, i), 1); } for (i = 0; i < PNP_MAX_MEM; i++) { -- cgit v0.10.2 From 10fccf5fda7529258325769e9da136064b481aab Mon Sep 17 00:00:00 2001 From: Bjorn Helgaas Date: Thu, 18 Jan 2007 16:44:24 -0700 Subject: i386: turn on CONFIG_PNP in defconfig I'm trying to remove drivers/acpi/motherboard.c, which is mostly redundant with drivers/pnp/system.c. So make sure that we include the PNP driver in the default config. Most distros enable this already. Turning on CONFIG_PNP also causes the following options to be enabled: CONFIG_PNPACPI CONFIG_SERIAL_8250_PNP CONFIG_SERIAL_8250_PNP causes legacy serial ports to be discovered twice, which is ugly but harmless: serial8250: ttyS0 at I/O 0x3f8 (irq = 4) is a 16550A 00:07: ttyS0 at I/O 0x3f8 (irq = 4) is a 16550A Signed-off-by: Bjorn Helgaas Signed-off-by: Len Brown diff --git a/arch/i386/defconfig b/arch/i386/defconfig index 3265208..7792792 100644 --- a/arch/i386/defconfig +++ b/arch/i386/defconfig @@ -466,7 +466,8 @@ CONFIG_FW_LOADER=y # # Plug and Play support # -# CONFIG_PNP is not set +CONFIG_PNP=y +CONFIG_PNPACPI=y # # Block devices -- cgit v0.10.2 From 5eca338fb510af78eee5372ff6a3525768ab913f Mon Sep 17 00:00:00 2001 From: Bjorn Helgaas Date: Thu, 18 Jan 2007 16:44:48 -0700 Subject: ACPI: remove motherboard driver (redundant with PNP system driver) The PNP system board driver (drivers/pnp/system.c) contains all the same functionality, so we don't need the ACPI version. Previously, a motherboard device would be claimed by *both* the ACPI and PNP drivers, resulting in stuff like this in /proc/ioports: 1200-121f : motherboard <-- from drivers/acpi/motherboard.c 1200-121f : pnp 00:0d <-- from drivers/pnp/system.c Make sure to enable CONFIG_PNP (and CONFIG_PNPACPI) to include the PNP system board driver. Signed-off-by: Bjorn Helgaas Signed-off-by: Len Brown diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile index a749510..62b3dd5 100644 --- a/drivers/acpi/Makefile +++ b/drivers/acpi/Makefile @@ -37,7 +37,7 @@ endif obj-y += sleep/ obj-y += bus.o glue.o -obj-y += scan.o motherboard.o +obj-y += scan.o obj-$(CONFIG_ACPI_AC) += ac.o obj-$(CONFIG_ACPI_BATTERY) += battery.o obj-$(CONFIG_ACPI_BUTTON) += button.o diff --git a/drivers/acpi/motherboard.c b/drivers/acpi/motherboard.c deleted file mode 100644 index cddab7b..0000000 --- a/drivers/acpi/motherboard.c +++ /dev/null @@ -1,131 +0,0 @@ -/* - * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or (at - * your option) any later version. - * - * This program is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * General Public License for more details. - * - * You should have received a copy of the GNU General Public License along - * with this program; if not, write to the Free Software Foundation, Inc., - * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. - * - * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - */ - -/* Purpose: Prevent PCMCIA cards from using motherboard resources. */ - -#include -#include -#include -#include -#include -#include - -#include -#include - -#define _COMPONENT ACPI_SYSTEM_COMPONENT -ACPI_MODULE_NAME("acpi_motherboard") - -/* Dell use PNP0C01 instead of PNP0C02 */ -#define ACPI_MB_HID "PNP0C01,PNP0C02" -/** - * Doesn't care about legacy IO ports, only IO ports beyond 0x1000 are reserved - * Doesn't care about the failure of 'request_region', since other may reserve - * the io ports as well - */ -#define IS_RESERVED_ADDR(base, len) \ - (((len) > 0) && ((base) > 0) && ((base) + (len) < IO_SPACE_LIMIT) \ - && ((base) + (len) > PCIBIOS_MIN_IO)) -/* - * Clearing the flag (IORESOURCE_BUSY) allows drivers to use - * the io ports if they really know they can use it, while - * still preventing hotplug PCI devices from using it. - */ - -/* - * When CONFIG_PNP is enabled, pnp/system.c binds to PNP0C01 - * and PNP0C02, redundant with acpi_reserve_io_ranges(). - * But acpi_reserve_io_ranges() is necessary for !CONFIG_PNP. - */ -static acpi_status acpi_reserve_io_ranges(struct acpi_resource *res, void *data) -{ - struct resource *requested_res = NULL; - - - if (res->type == ACPI_RESOURCE_TYPE_IO) { - struct acpi_resource_io *io_res = &res->data.io; - - if (io_res->minimum != io_res->maximum) - return AE_OK; - if (IS_RESERVED_ADDR - (io_res->minimum, io_res->address_length)) { - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Motherboard resources 0x%08x - 0x%08x\n", - io_res->minimum, - io_res->minimum + - io_res->address_length)); - requested_res = - request_region(io_res->minimum, - io_res->address_length, "motherboard"); - } - } else if (res->type == ACPI_RESOURCE_TYPE_FIXED_IO) { - struct acpi_resource_fixed_io *fixed_io_res = - &res->data.fixed_io; - - if (IS_RESERVED_ADDR - (fixed_io_res->address, fixed_io_res->address_length)) { - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Motherboard resources 0x%08x - 0x%08x\n", - fixed_io_res->address, - fixed_io_res->address + - fixed_io_res->address_length)); - requested_res = - request_region(fixed_io_res->address, - fixed_io_res->address_length, - "motherboard"); - } - } else { - /* Memory mapped IO? */ - } - - if (requested_res) - requested_res->flags &= ~IORESOURCE_BUSY; - return AE_OK; -} - -static int acpi_motherboard_add(struct acpi_device *device) -{ - if (!device) - return -EINVAL; - acpi_walk_resources(device->handle, METHOD_NAME__CRS, - acpi_reserve_io_ranges, NULL); - - return 0; -} - -static struct acpi_driver acpi_motherboard_driver = { - .name = "motherboard", - .class = "", - .ids = ACPI_MB_HID, - .ops = { - .add = acpi_motherboard_add, - }, -}; - -static int __init acpi_motherboard_init(void) -{ - acpi_bus_register_driver(&acpi_motherboard_driver); - return 0; -} - -/** - * Reserve motherboard resources after PCI claim BARs, - * but before PCI assign resources for uninitialized PCI devices - */ -fs_initcall(acpi_motherboard_init); -- cgit v0.10.2 From fb5c3e1b6d304bcf5f8d697471e36f2fa8d53f1c Mon Sep 17 00:00:00 2001 From: Bjorn Helgaas Date: Wed, 24 Jan 2007 00:49:19 -0800 Subject: PNPACPI: remove EXPERIMENTAL dependency PNPACPI is pretty widely used and seems fairly stable, so remove the dependency on EXPERIMENTAL. Signed-off-by: Bjorn Helgaas Cc: Adam Belay Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/drivers/pnp/pnpacpi/Kconfig b/drivers/pnp/pnpacpi/Kconfig index b185417..ad27e5e 100644 --- a/drivers/pnp/pnpacpi/Kconfig +++ b/drivers/pnp/pnpacpi/Kconfig @@ -2,8 +2,8 @@ # Plug and Play ACPI configuration # config PNPACPI - bool "Plug and Play ACPI support (EXPERIMENTAL)" - depends on PNP && ACPI && EXPERIMENTAL + bool "Plug and Play ACPI support" + depends on PNP && ACPI default y ---help--- Linux uses the PNPACPI to autodetect built-in -- cgit v0.10.2 From b981c591891dc8885de36498d38fa8d8a5481069 Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Mon, 29 Jan 2007 11:02:30 +0800 Subject: ACPI: add a Kconfig option for ACPI procfs interface Add a kconfig option CONFIG_ACPI_PROCFS to make procfs interface a configurable attribute of ACPI. No procfs interface is actually deprecated, and no sysfs interface is added in this patch. CONGI_ACPI_PROCFS is used to mark procfs interface as deprecated once the same function is duplicated in sysfs. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/Documentation/feature-removal-schedule.txt b/Documentation/feature-removal-schedule.txt index 30f3c8c..9bc3752 100644 --- a/Documentation/feature-removal-schedule.txt +++ b/Documentation/feature-removal-schedule.txt @@ -256,3 +256,12 @@ Why: Speedstep-centrino driver with ACPI hooks and acpi-cpufreq driver are Who: Venkatesh Pallipadi --------------------------- + +What: ACPI procfs interface +When: July 2007 +Why: After ACPI sysfs conversion, ACPI attributes will be duplicated + in sysfs and the ACPI procfs interface should be removed. +Who: Zhang Rui + +--------------------------- + diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index 0f9d4be..1f82ceb 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -77,6 +77,16 @@ config ACPI_SLEEP_PROC_SLEEP Create /proc/acpi/sleep Deprecated by /sys/power/state +config ACPI_PROCFS + bool "Procfs interface (deprecated)" + depends on ACPI + default y + ---help--- + Procfs interface for ACPI is made optional for back-compatible. + As the same functions are duplicated in sysfs interface + and this proc interface will be removed some time later, + it's marked as deprecated. + config ACPI_AC tristate "AC Adapter" depends on X86 -- cgit v0.10.2 From 219c3c8e268b9307eae9fae4c765a0c589b98338 Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Mon, 29 Jan 2007 11:02:38 +0800 Subject: ACPI: add ACPI debug attribute in sysfs Add ACPI debug attributes in sysfs. /proc/acpi/debug_layer && debug_level are deprecated by /sys/module/acpi/parameters/debug_layer && debug_level. NOTE: The operations to them are quite the same. E.g. if you want to enable ACPI_DB_INFO, ACPI_DB_WARN, ACPI_DB_ERROR and disable the others, #echo 0x13 >/sys/module/acpi/parameters/debug_level is OK, and a boot option "acpi.debug_level = 0x13" also works. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index 1f82ceb..a3a1073 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -86,6 +86,8 @@ config ACPI_PROCFS As the same functions are duplicated in sysfs interface and this proc interface will be removed some time later, it's marked as deprecated. + ( /proc/acpi/debug_layer && debug_level are deprecated by + /sys/module/acpi/parameters/debug_layer && debug_level. ) config ACPI_AC tristate "AC Adapter" diff --git a/drivers/acpi/debug.c b/drivers/acpi/debug.c index 35c6af8..d48f65a 100644 --- a/drivers/acpi/debug.c +++ b/drivers/acpi/debug.c @@ -13,14 +13,11 @@ #define _COMPONENT ACPI_SYSTEM_COMPONENT ACPI_MODULE_NAME("debug") -#define ACPI_SYSTEM_FILE_DEBUG_LAYER "debug_layer" -#define ACPI_SYSTEM_FILE_DEBUG_LEVEL "debug_level" + #ifdef MODULE_PARAM_PREFIX #undef MODULE_PARAM_PREFIX #endif -#define MODULE_PARAM_PREFIX - module_param(acpi_dbg_layer, uint, 0400); -module_param(acpi_dbg_level, uint, 0400); +#define MODULE_PARAM_PREFIX "acpi." struct acpi_dlayer { const char *name; @@ -86,6 +83,60 @@ static const struct acpi_dlevel acpi_debug_levels[] = { ACPI_DEBUG_INIT(ACPI_LV_EVENTS), }; +/* -------------------------------------------------------------------------- + FS Interface (/sys) + -------------------------------------------------------------------------- */ +static int param_get_debug_layer(char *buffer, struct kernel_param *kp) { + int result = 0; + int i; + + result = sprintf(buffer, "%-25s\tHex SET\n", "Description"); + + for(i = 0; i Date: Mon, 29 Jan 2007 11:02:42 +0800 Subject: ACPI: add ACPICA version in sysfs Add an ACPI attribute to indicate ACPICA version. /proc/acpi/version is deprecated by /sys/module/acpi/parameters/acpica_version. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index a3a1073..df45144 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -87,7 +87,9 @@ config ACPI_PROCFS and this proc interface will be removed some time later, it's marked as deprecated. ( /proc/acpi/debug_layer && debug_level are deprecated by - /sys/module/acpi/parameters/debug_layer && debug_level. ) + /sys/module/acpi/parameters/debug_layer && debug_level. + /proc/acpi/info is deprecated by + /sys/module/acpi/parameters/acpica_version ) config ACPI_AC tristate "AC Adapter" diff --git a/drivers/acpi/system.c b/drivers/acpi/system.c index d86dcb3..407b0e0 100644 --- a/drivers/acpi/system.c +++ b/drivers/acpi/system.c @@ -32,6 +32,11 @@ #define _COMPONENT ACPI_SYSTEM_COMPONENT ACPI_MODULE_NAME("acpi_system") +#ifdef MODULE_PARAM_PREFIX +#undef MODULE_PARAM_PREFIX +#endif +#define MODULE_PARAM_PREFIX "acpi." + #define ACPI_SYSTEM_CLASS "system" #define ACPI_SYSTEM_DRIVER_NAME "ACPI System Driver" #define ACPI_SYSTEM_DEVICE_NAME "System" @@ -41,9 +46,23 @@ ACPI_MODULE_NAME("acpi_system") #define ACPI_SYSTEM_FILE_FADT "fadt" extern struct fadt_descriptor acpi_fadt; +/* + * Make ACPICA version work as module param + */ +static int param_get_acpica_version(char *buffer, struct kernel_param *kp) { + int result; + + result = sprintf(buffer, "%x", ACPI_CA_VERSION); + + return result; +} + +module_param_call(acpica_version, NULL, param_get_acpica_version, NULL, 0444); + /* -------------------------------------------------------------------------- FS Interface (/proc) -------------------------------------------------------------------------- */ +#ifdef CONFIG_ACPI_PROCFS static int acpi_system_read_info(struct seq_file *seq, void *offset) { @@ -63,6 +82,7 @@ static const struct file_operations acpi_system_info_ops = { .llseek = seq_lseek, .release = single_release, }; +#endif static ssize_t acpi_system_read_dsdt(struct file *, char __user *, size_t, loff_t *); @@ -128,6 +148,7 @@ static int __init acpi_system_init(void) if (acpi_disabled) return 0; +#ifdef CONFIG_ACPI_PROCFS /* 'info' [R] */ name = ACPI_SYSTEM_FILE_INFO; entry = create_proc_entry(name, S_IRUGO, acpi_root_dir); @@ -136,6 +157,7 @@ static int __init acpi_system_init(void) else { entry->proc_fops = &acpi_system_info_ops; } +#endif /* 'dsdt' [R] */ name = ACPI_SYSTEM_FILE_DSDT; @@ -159,7 +181,9 @@ static int __init acpi_system_init(void) Error: remove_proc_entry(ACPI_SYSTEM_FILE_FADT, acpi_root_dir); remove_proc_entry(ACPI_SYSTEM_FILE_DSDT, acpi_root_dir); +#ifdef CONFIG_ACPI_PROCFS remove_proc_entry(ACPI_SYSTEM_FILE_INFO, acpi_root_dir); +#endif error = -EFAULT; goto Done; -- cgit v0.10.2 From 85091b718969be7b8e6f795af7e264b8afcd7a6d Mon Sep 17 00:00:00 2001 From: Corentin Chary Date: Fri, 26 Jan 2007 14:04:30 +0100 Subject: asus-laptop: add base driver Adds the new driver and make ASUS_LAPTOP and ACPI_ASUS incompatible. It may be strange to use ASUS_CREATE_DEVICE_ATTR and ASUS_SET_DEVICE_ATTR now, but these macro will be very usefull in next patchs. ASUS_HANDLE and ASUS_HANDLE_INIT comes from IBM_HANDLE and IBM_HANDLE_INIT, with some modification, and will also be used in next patchs. Signed-off-by: Corentin Chary Signed-off-by: Len Brown diff --git a/MAINTAINERS b/MAINTAINERS index f0596e4..515289a 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -584,6 +584,14 @@ W: http://sourceforge.net/projects/acpi4asus W: http://xf.iksaif.net/acpi4asus S: Maintained +ASUS LAPTOP EXTRAS DRIVER +P: Corentin Chary +M: corentincj@iksaif.net +L: acpi4asus-user@lists.sourceforge.net +W: http://sourceforge.net/projects/acpi4asus +W: http://xf.iksaif.net/acpi4asus +S: Maintained + ATA OVER ETHERNET DRIVER P: Ed L. Cashin M: ecashin@coraid.com diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index f4f000a..deed0de 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -186,19 +186,22 @@ config ACPI_ASUS Note: display switching code is currently considered EXPERIMENTAL, toying with these values may even lock your machine. - + All settings are changed via /proc/acpi/asus directory entries. Owner and group for these entries can be set with asus_uid and asus_gid parameters. - + More information and a userspace daemon for handling the extra buttons at . - + If you have an ACPI-compatible ASUS laptop, say Y or M here. This driver is still under development, so if your laptop is unsupported or something works not quite as expected, please use the mailing list - available on the above page (acpi4asus-user@lists.sourceforge.net) - + available on the above page (acpi4asus-user@lists.sourceforge.net). + + NOTE: This driver is deprecated and will probably be removed soon, + use asus-laptop instead. + config ACPI_IBM tristate "IBM ThinkPad Laptop Extras" depends on X86 diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig index 00db31c..4b1e367 100644 --- a/drivers/misc/Kconfig +++ b/drivers/misc/Kconfig @@ -69,6 +69,23 @@ config TIFM_7XX1 To compile this driver as a module, choose M here: the module will be called tifm_7xx1. +config ASUS_LAPTOP + tristate "Asus Laptop Extras (EXPERIMENTAL)" + depends on X86 + depends on ACPI + depends on EXPERIMENTAL && !ACPI_ASUS + ---help--- + This is the new Linux driver for Asus laptops. It may also support some + MEDION, JVC or VICTOR laptops. It makes all the extra buttons generate + standard ACPI events that go through /proc/acpi/events. It also adds + support for video output switching, LCD backlight control, Bluetooth and + Wlan control, and most importantly, allows you to blink those fancy LEDs. + + For more information and a userspace daemon for handling the extra + buttons see . + + If you have an ACPI-compatible ASUS laptop, say Y or M here. + config MSI_LAPTOP tristate "MSI Laptop Extras" depends on X86 diff --git a/drivers/misc/Makefile b/drivers/misc/Makefile index c9e98ab..35da53c 100644 --- a/drivers/misc/Makefile +++ b/drivers/misc/Makefile @@ -6,6 +6,7 @@ obj- := misc.o # Dummy rule to force built-in.o to be made obj-$(CONFIG_IBM_ASM) += ibmasm/ obj-$(CONFIG_HDPU_FEATURES) += hdpuftrs/ obj-$(CONFIG_MSI_LAPTOP) += msi-laptop.o +obj-$(CONFIG_ASUS_LAPTOP) += asus-laptop.o obj-$(CONFIG_LKDTM) += lkdtm.o obj-$(CONFIG_TIFM_CORE) += tifm_core.o obj-$(CONFIG_TIFM_7XX1) += tifm_7xx1.o diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c new file mode 100644 index 0000000..959b20f --- /dev/null +++ b/drivers/misc/asus-laptop.c @@ -0,0 +1,530 @@ +/* + * asus-laptop.c - Asus Laptop Support + * + * + * Copyright (C) 2002-2005 Julien Lerouge, 2003-2006 Karol Kozimor + * Copyright (C) 2006 Corentin Chary + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + * + * The development page for this driver is located at + * http://sourceforge.net/projects/acpi4asus/ + * + * Credits: + * Pontus Fuchs - Helper functions, cleanup + * Johann Wiesner - Small compile fixes + * John Belmonte - ACPI code for Toshiba laptop was a good starting point. + * Eric Burghard - LED display support for W1N + * Josh Green - Light Sens support + * Thomas Tuttle - His first patch for led support was very helpfull + * + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define ASUS_LAPTOP_VERSION "0.40" + +#define ASUS_HOTK_NAME "Asus Laptop Support" +#define ASUS_HOTK_CLASS "hotkey" +#define ASUS_HOTK_DEVICE_NAME "Hotkey" +#define ASUS_HOTK_HID "ATK0100" +#define ASUS_HOTK_FILE "asus-laptop" +#define ASUS_HOTK_PREFIX "\\_SB.ATKD." + +#define ASUS_LOG ASUS_HOTK_FILE ": " +#define ASUS_ERR KERN_ERR ASUS_LOG +#define ASUS_WARNING KERN_WARNING ASUS_LOG +#define ASUS_NOTICE KERN_NOTICE ASUS_LOG +#define ASUS_INFO KERN_INFO ASUS_LOG +#define ASUS_DEBUG KERN_DEBUG ASUS_LOG + +MODULE_AUTHOR("Julien Lerouge, Karol Kozimor, Corentin Chary"); +MODULE_DESCRIPTION(ASUS_HOTK_NAME); +MODULE_LICENSE("GPL"); + +#define ASUS_HANDLE(object, paths...) \ + static acpi_handle object##_handle = NULL; \ + static char *object##_paths[] = { paths } + +/* + * This is the main structure, we can use it to store anything interesting + * about the hotk device + */ +struct asus_hotk { + char *name; //laptop name + struct acpi_device *device; //the device we are in + acpi_handle handle; //the handle of the hotk device + char status; //status of the hotk, for LEDs, ... + u16 event_count[128]; //count for each event TODO make this better +}; + +/* + * This header is made available to allow proper configuration given model, + * revision number , ... this info cannot go in struct asus_hotk because it is + * available before the hotk + */ +static struct acpi_table_header *asus_info; + +/* The actual device the driver binds to */ +static struct asus_hotk *hotk; + +/* + * The hotkey driver declaration + */ +static int asus_hotk_add(struct acpi_device *device); +static int asus_hotk_remove(struct acpi_device *device, int type); +static struct acpi_driver asus_hotk_driver = { + .name = ASUS_HOTK_NAME, + .class = ASUS_HOTK_CLASS, + .ids = ASUS_HOTK_HID, + .ops = { + .add = asus_hotk_add, + .remove = asus_hotk_remove, + }, +}; + +/* + * This function evaluates an ACPI method, given an int as parameter, the + * method is searched within the scope of the handle, can be NULL. The output + * of the method is written is output, which can also be NULL + * + * returns 1 if write is successful, 0 else. + */ +static int write_acpi_int(acpi_handle handle, const char *method, int val, + struct acpi_buffer *output) +{ + struct acpi_object_list params; //list of input parameters (an int here) + union acpi_object in_obj; //the only param we use + acpi_status status; + + params.count = 1; + params.pointer = &in_obj; + in_obj.type = ACPI_TYPE_INTEGER; + in_obj.integer.value = val; + + status = acpi_evaluate_object(handle, (char *)method, ¶ms, output); + return (status == AE_OK); +} + +static int read_acpi_int(acpi_handle handle, const char *method, int *val, + struct acpi_object_list *params) +{ + struct acpi_buffer output; + union acpi_object out_obj; + acpi_status status; + + output.length = sizeof(out_obj); + output.pointer = &out_obj; + + status = acpi_evaluate_object(handle, (char *)method, params, &output); + *val = out_obj.integer.value; + return (status == AE_OK) && (out_obj.type == ACPI_TYPE_INTEGER); +} + +/* + * Platform device handlers + */ + +/* + * We write our info in page, we begin at offset off and cannot write more + * than count bytes. We set eof to 1 if we handle those 2 values. We return the + * number of bytes written in page + */ +static ssize_t show_infos(struct device *dev, + struct device_attribute *attr, char *page) +{ + int len = 0; + int temp; + char buf[16]; //enough for all info + /* + * We use the easy way, we don't care of off and count, so we don't set eof + * to 1 + */ + + len += sprintf(page, ASUS_HOTK_NAME " " ASUS_LAPTOP_VERSION "\n"); + len += sprintf(page + len, "Model reference : %s\n", hotk->name); + /* + * The SFUN method probably allows the original driver to get the list + * of features supported by a given model. For now, 0x0100 or 0x0800 + * bit signifies that the laptop is equipped with a Wi-Fi MiniPCI card. + * The significance of others is yet to be found. + */ + if (read_acpi_int(hotk->handle, "SFUN", &temp, NULL)) + len += + sprintf(page + len, "SFUN value : 0x%04x\n", temp); + /* + * Another value for userspace: the ASYM method returns 0x02 for + * battery low and 0x04 for battery critical, its readings tend to be + * more accurate than those provided by _BST. + * Note: since not all the laptops provide this method, errors are + * silently ignored. + */ + if (read_acpi_int(hotk->handle, "ASYM", &temp, NULL)) + len += + sprintf(page + len, "ASYM value : 0x%04x\n", temp); + if (asus_info) { + snprintf(buf, 16, "%d", asus_info->length); + len += sprintf(page + len, "DSDT length : %s\n", buf); + snprintf(buf, 16, "%d", asus_info->checksum); + len += sprintf(page + len, "DSDT checksum : %s\n", buf); + snprintf(buf, 16, "%d", asus_info->revision); + len += sprintf(page + len, "DSDT revision : %s\n", buf); + snprintf(buf, 7, "%s", asus_info->oem_id); + len += sprintf(page + len, "OEM id : %s\n", buf); + snprintf(buf, 9, "%s", asus_info->oem_table_id); + len += sprintf(page + len, "OEM table id : %s\n", buf); + snprintf(buf, 16, "%x", asus_info->oem_revision); + len += sprintf(page + len, "OEM revision : 0x%s\n", buf); + snprintf(buf, 5, "%s", asus_info->asl_compiler_id); + len += sprintf(page + len, "ASL comp vendor id : %s\n", buf); + snprintf(buf, 16, "%x", asus_info->asl_compiler_revision); + len += sprintf(page + len, "ASL comp revision : 0x%s\n", buf); + } + + return len; +} + +static int parse_arg(const char *buf, unsigned long count, int *val) +{ + if (!count) + return 0; + if (count > 31) + return -EINVAL; + if (sscanf(buf, "%i", val) != 1) + return -EINVAL; + return count; +} + +static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) +{ + /* TODO Find a better way to handle events count. */ + if (!hotk) + return; + + acpi_bus_generate_event(hotk->device, event, + hotk->event_count[event % 128]++); + + return; +} + +#define ASUS_CREATE_DEVICE_ATTR(_name) \ + struct device_attribute dev_attr_##_name = { \ + .attr = { \ + .name = __stringify(_name), \ + .mode = 0, \ + .owner = THIS_MODULE }, \ + .show = NULL, \ + .store = NULL, \ + } + +#define ASUS_SET_DEVICE_ATTR(_name, _mode, _show, _store) \ + do { \ + dev_attr_##_name.attr.mode = _mode; \ + dev_attr_##_name.show = _show; \ + dev_attr_##_name.store = _store; \ + } while(0) + +static ASUS_CREATE_DEVICE_ATTR(infos); + +static struct attribute *asuspf_attributes[] = { + &dev_attr_infos.attr, + NULL +}; + +static struct attribute_group asuspf_attribute_group = { + .attrs = asuspf_attributes +}; + +static struct platform_driver asuspf_driver = { + .driver = { + .name = ASUS_HOTK_FILE, + .owner = THIS_MODULE, + } +}; + +static struct platform_device *asuspf_device; + + +static void asus_hotk_add_fs(void) +{ + ASUS_SET_DEVICE_ATTR(infos, 0444, show_infos, NULL); +} + +static int asus_handle_init(char *name, acpi_handle *handle, + char **paths, int num_paths) +{ + int i; + acpi_status status; + + for (i = 0; i < num_paths; i++) { + status = acpi_get_handle(NULL, paths[i], handle); + if (ACPI_SUCCESS(status)) + return 0; + } + + *handle = NULL; + return -ENODEV; +} + +#define ASUS_HANDLE_INIT(object) \ + asus_handle_init(#object, &object##_handle, object##_paths, \ + ARRAY_SIZE(object##_paths)) + + +/* + * This function is used to initialize the hotk with right values. In this + * method, we can make all the detection we want, and modify the hotk struct + */ +static int asus_hotk_get_info(void) +{ + struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; + struct acpi_buffer dsdt = { ACPI_ALLOCATE_BUFFER, NULL }; + union acpi_object *model = NULL; + int bsts_result; + char *string = NULL; + acpi_status status; + + /* + * Get DSDT headers early enough to allow for differentiating between + * models, but late enough to allow acpi_bus_register_driver() to fail + * before doing anything ACPI-specific. Should we encounter a machine, + * which needs special handling (i.e. its hotkey device has a different + * HID), this bit will be moved. A global variable asus_info contains + * the DSDT header. + */ + status = acpi_get_table(ACPI_TABLE_ID_DSDT, 1, &dsdt); + if (ACPI_FAILURE(status)) + printk(ASUS_WARNING "Couldn't get the DSDT table header\n"); + else + asus_info = dsdt.pointer; + + /* We have to write 0 on init this far for all ASUS models */ + if (!write_acpi_int(hotk->handle, "INIT", 0, &buffer)) { + printk(ASUS_ERR "Hotkey initialization failed\n"); + return -ENODEV; + } + + /* This needs to be called for some laptops to init properly */ + if (!read_acpi_int(hotk->handle, "BSTS", &bsts_result, NULL)) + printk(ASUS_WARNING "Error calling BSTS\n"); + else if (bsts_result) + printk(ASUS_NOTICE "BSTS called, 0x%02x returned\n", + bsts_result); + + /* + * Try to match the object returned by INIT to the specific model. + * Handle every possible object (or the lack of thereof) the DSDT + * writers might throw at us. When in trouble, we pass NULL to + * asus_model_match() and try something completely different. + */ + if (buffer.pointer) { + model = buffer.pointer; + switch (model->type) { + case ACPI_TYPE_STRING: + string = model->string.pointer; + break; + case ACPI_TYPE_BUFFER: + string = model->buffer.pointer; + break; + default: + string = ""; + break; + } + } + hotk->name = kstrdup(string, GFP_KERNEL); + if (!hotk->name) + return -ENOMEM; + + if(*string) + printk(ASUS_NOTICE " %s model detected\n", string); + + kfree(model); + + return AE_OK; +} + +static int asus_hotk_check(void) +{ + int result = 0; + + result = acpi_bus_get_status(hotk->device); + if (result) + return result; + + if (hotk->device->status.present) { + result = asus_hotk_get_info(); + } else { + printk(ASUS_ERR "Hotkey device not present, aborting\n"); + return -EINVAL; + } + + return result; +} + +static int asus_hotk_found; + +static int asus_hotk_add(struct acpi_device *device) +{ + acpi_status status = AE_OK; + int result; + + if (!device) + return -EINVAL; + + printk(ASUS_NOTICE "Asus Laptop Support version %s\n", + ASUS_LAPTOP_VERSION); + + hotk = kmalloc(sizeof(struct asus_hotk), GFP_KERNEL); + if (!hotk) + return -ENOMEM; + memset(hotk, 0, sizeof(struct asus_hotk)); + + hotk->handle = device->handle; + strcpy(acpi_device_name(device), ASUS_HOTK_DEVICE_NAME); + strcpy(acpi_device_class(device), ASUS_HOTK_CLASS); + acpi_driver_data(device) = hotk; + hotk->device = device; + + result = asus_hotk_check(); + if (result) + goto end; + + asus_hotk_add_fs(); + + /* + * We install the handler, it will receive the hotk in parameter, so, we + * could add other data to the hotk struct + */ + status = acpi_install_notify_handler(hotk->handle, ACPI_SYSTEM_NOTIFY, + asus_hotk_notify, hotk); + if (ACPI_FAILURE(status)) + printk(ASUS_ERR "Error installing notify handler\n"); + + asus_hotk_found = 1; + + end: + if (result) { + kfree(hotk->name); + kfree(hotk); + } + + return result; +} + +static int asus_hotk_remove(struct acpi_device *device, int type) +{ + acpi_status status = 0; + + if (!device || !acpi_driver_data(device)) + return -EINVAL; + + status = acpi_remove_notify_handler(hotk->handle, ACPI_SYSTEM_NOTIFY, + asus_hotk_notify); + if (ACPI_FAILURE(status)) + printk(ASUS_ERR "Error removing notify handler\n"); + + kfree(hotk->name); + kfree(hotk); + + return 0; +} + +static void __exit asus_laptop_exit(void) +{ + acpi_bus_unregister_driver(&asus_hotk_driver); + sysfs_remove_group(&asuspf_device->dev.kobj, &asuspf_attribute_group); + platform_device_unregister(asuspf_device); + platform_driver_unregister(&asuspf_driver); + + kfree(asus_info); +} + +static int __init asus_laptop_init(void) +{ + int result; + + if (acpi_disabled) + return -ENODEV; + + if (!acpi_specific_hotkey_enabled) { + printk(ASUS_ERR "Using generic hotkey driver\n"); + return -ENODEV; + } + + result = acpi_bus_register_driver(&asus_hotk_driver); + if (result < 0) + return result; + + /* + * This is a bit of a kludge. We only want this module loaded + * for ASUS systems, but there's currently no way to probe the + * ACPI namespace for ASUS HIDs. So we just return failure if + * we didn't find one, which will cause the module to be + * unloaded. + */ + if (!asus_hotk_found) { + acpi_bus_unregister_driver(&asus_hotk_driver); + return -ENODEV; + } + + /* Register platform stuff */ + result = platform_driver_register(&asuspf_driver); + if (result) + goto fail_platform_driver; + + asuspf_device = platform_device_alloc(ASUS_HOTK_FILE, -1); + if (!asuspf_device) { + result = -ENOMEM; + goto fail_platform_device1; + } + + result = platform_device_add(asuspf_device); + if (result) + goto fail_platform_device2; + + result = sysfs_create_group(&asuspf_device->dev.kobj, + &asuspf_attribute_group); + if (result) + goto fail_sysfs; + + return 0; + +fail_sysfs: + platform_device_del(asuspf_device); + +fail_platform_device2: + platform_device_put(asuspf_device); + +fail_platform_device1: + platform_driver_unregister(&asuspf_driver); + +fail_platform_driver: + + return result; +} + +module_init(asus_laptop_init); +module_exit(asus_laptop_exit); -- cgit v0.10.2 From be18cdabb8ed40ff4b8a240e0d6f4e6c30ff866d Mon Sep 17 00:00:00 2001 From: Corentin Chary Date: Fri, 26 Jan 2007 14:04:35 +0100 Subject: asus-laptop: add led support Add led support, using generic led class. Thomas Tuttle's patch was very usefull. We use hotk->status to store led status because it's very hard to find acpi method to get the right status... To reduce the code, I use a lot of macro (ASUS_LED, ASUS_LED_REGISTER, etc ...), because the code is the same for all leds ... Signed-off-by: Corentin Chary Signed-off-by: Len Brown diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig index 4b1e367..87e1db8 100644 --- a/drivers/misc/Kconfig +++ b/drivers/misc/Kconfig @@ -74,6 +74,7 @@ config ASUS_LAPTOP depends on X86 depends on ACPI depends on EXPERIMENTAL && !ACPI_ASUS + depends on LEDS_CLASS ---help--- This is the new Linux driver for Asus laptops. It may also support some MEDION, JVC or VICTOR laptops. It makes all the extra buttons generate diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index 959b20f..d0d5ee9 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -40,6 +40,7 @@ #include #include #include +#include #include #include #include @@ -54,6 +55,14 @@ #define ASUS_HOTK_FILE "asus-laptop" #define ASUS_HOTK_PREFIX "\\_SB.ATKD." +/* + * Flags for hotk status + */ +#define MLED_ON 0x04 //mail LED +#define TLED_ON 0x08 //touchpad LED +#define RLED_ON 0x10 //Record LED +#define PLED_ON 0x20 //Phone LED + #define ASUS_LOG ASUS_HOTK_FILE ": " #define ASUS_ERR KERN_ERR ASUS_LOG #define ASUS_WARNING KERN_WARNING ASUS_LOG @@ -69,6 +78,12 @@ MODULE_LICENSE("GPL"); static acpi_handle object##_handle = NULL; \ static char *object##_paths[] = { paths } +/* LED */ +ASUS_HANDLE(mled_set, ASUS_HOTK_PREFIX "MLED"); +ASUS_HANDLE(tled_set, ASUS_HOTK_PREFIX "TLED"); +ASUS_HANDLE(rled_set, ASUS_HOTK_PREFIX "RLED"); /* W1JC */ +ASUS_HANDLE(pled_set, ASUS_HOTK_PREFIX "PLED"); /* A7J */ + /* * This is the main structure, we can use it to store anything interesting * about the hotk device @@ -106,6 +121,28 @@ static struct acpi_driver asus_hotk_driver = { }, }; +/* These functions actually update the LED's, and are called from a + * workqueue. By doing this as separate work rather than when the LED + * subsystem asks, we avoid messing with the Asus ACPI stuff during a + * potentially bad time, such as a timer interrupt. */ +static struct workqueue_struct *led_workqueue; + +#define ASUS_LED(object, ledname) \ + static void object##_led_set(struct led_classdev *led_cdev, \ + enum led_brightness value); \ + static void object##_led_update(struct work_struct *ignored); \ + static int object##_led_wk; \ + DECLARE_WORK(object##_led_work, object##_led_update); \ + static struct led_classdev object##_led = { \ + .name = "asus:" ledname, \ + .brightness_set = object##_led_set, \ + } + +ASUS_LED(mled, "mail"); +ASUS_LED(tled, "touchpad"); +ASUS_LED(rled, "record"); +ASUS_LED(pled, "phone"); + /* * This function evaluates an ACPI method, given an int as parameter, the * method is searched within the scope of the handle, can be NULL. The output @@ -144,6 +181,43 @@ static int read_acpi_int(acpi_handle handle, const char *method, int *val, return (status == AE_OK) && (out_obj.type == ACPI_TYPE_INTEGER); } +/* Generic LED functions */ +static int read_status(int mask) +{ + return (hotk->status & mask) ? 1 : 0; +} + +static void write_status(acpi_handle handle, int out, int mask, + int invert) +{ + hotk->status = (out) ? (hotk->status | mask) : (hotk->status & ~mask); + + if (invert) /* invert target value */ + out = !out & 0x1; + + if (handle && !write_acpi_int(handle, NULL, out, NULL)) + printk(ASUS_WARNING " write failed\n"); +} + +/* /sys/class/led handlers */ +#define ASUS_LED_HANDLER(object, mask, invert) \ + static void object##_led_set(struct led_classdev *led_cdev, \ + enum led_brightness value) \ + { \ + object##_led_wk = value; \ + queue_work(led_workqueue, &object##_led_work); \ + } \ + static void object##_led_update(struct work_struct *ignored) \ + { \ + int value = object##_led_wk; \ + write_status(object##_set_handle, value, (mask), (invert)); \ + } + +ASUS_LED_HANDLER(mled, MLED_ON, 1); +ASUS_LED_HANDLER(pled, PLED_ON, 0); +ASUS_LED_HANDLER(rled, RLED_ON, 0); +ASUS_LED_HANDLER(tled, TLED_ON, 0); + /* * Platform device handlers */ @@ -361,6 +435,11 @@ static int asus_hotk_get_info(void) if(*string) printk(ASUS_NOTICE " %s model detected\n", string); + ASUS_HANDLE_INIT(mled_set); + ASUS_HANDLE_INIT(tled_set); + ASUS_HANDLE_INIT(rled_set); + ASUS_HANDLE_INIT(pled_set); + kfree(model); return AE_OK; @@ -452,8 +531,25 @@ static int asus_hotk_remove(struct acpi_device *device, int type) return 0; } +#define ASUS_LED_UNREGISTER(object) \ + if(object##_led.class_dev \ + && !IS_ERR(object##_led.class_dev)) \ + led_classdev_unregister(&object##_led) + +static void asus_led_exit(void) +{ + ASUS_LED_UNREGISTER(mled); + ASUS_LED_UNREGISTER(tled); + ASUS_LED_UNREGISTER(pled); + ASUS_LED_UNREGISTER(rled); + + destroy_workqueue(led_workqueue); +} + static void __exit asus_laptop_exit(void) { + asus_led_exit(); + acpi_bus_unregister_driver(&asus_hotk_driver); sysfs_remove_group(&asuspf_device->dev.kobj, &asuspf_attribute_group); platform_device_unregister(asuspf_device); @@ -462,8 +558,48 @@ static void __exit asus_laptop_exit(void) kfree(asus_info); } +static int asus_led_register(acpi_handle handle, + struct led_classdev * ldev, + struct device * dev) +{ + if(!handle) + return 0; + + return led_classdev_register(dev, ldev); +} +#define ASUS_LED_REGISTER(object, device) \ + asus_led_register(object##_set_handle, &object##_led, device) + +static int asus_led_init(struct device * dev) +{ + int rv; + + rv = ASUS_LED_REGISTER(mled, dev); + if(rv) + return rv; + + rv = ASUS_LED_REGISTER(tled, dev); + if(rv) + return rv; + + rv = ASUS_LED_REGISTER(rled, dev); + if(rv) + return rv; + + rv = ASUS_LED_REGISTER(pled, dev); + if(rv) + return rv; + + led_workqueue = create_singlethread_workqueue("led_workqueue"); + if(!led_workqueue) + return -ENOMEM; + + return 0; +} + static int __init asus_laptop_init(void) { + struct device *dev; int result; if (acpi_disabled) @@ -490,6 +626,12 @@ static int __init asus_laptop_init(void) return -ENODEV; } + dev = acpi_get_physical_device(hotk->device->handle); + + result = asus_led_init(dev); + if(result) + goto fail_led; + /* Register platform stuff */ result = platform_driver_register(&asuspf_driver); if (result) @@ -522,6 +664,9 @@ fail_platform_device1: platform_driver_unregister(&asuspf_driver); fail_platform_driver: + asus_led_exit(); + +fail_led: return result; } -- cgit v0.10.2 From 4564de172dcdce641c0d6c689e79e95b5f6bee2c Mon Sep 17 00:00:00 2001 From: Corentin Chary Date: Fri, 26 Jan 2007 14:04:40 +0100 Subject: asus-laptop: add bluetooth and wlan support WLED and BLED are not handled like other leds (MLED, etc ..), because sometime they also control the wlan/bluetooth device. If the method for wireless_status is found, it's used to get the status, otherwise hotk->status is used. We also use the HWRS method, which tell if the bluetooth/wlan device is present or not. This patch show why we need a ASUS_SET_DEVICE_ATTR macro : if there is a bluetooth device, /sys/dev.../asus-laptop/bluetooth is usable, else it's not but it's clean. Signed-off-by: Corentin Chary Signed-off-by: Len Brown diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index d0d5ee9..222d4fb 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -56,8 +56,17 @@ #define ASUS_HOTK_PREFIX "\\_SB.ATKD." /* + * Known bits returned by \_SB.ATKD.HWRS + */ +#define WL_HWRS 0x80 +#define BT_HWRS 0x100 + +/* * Flags for hotk status + * WL_ON and BT_ON are also used for wireless_status() */ +#define WL_ON 0x01 //internal Wifi +#define BT_ON 0x02 //internal Bluetooth #define MLED_ON 0x04 //mail LED #define TLED_ON 0x08 //touchpad LED #define RLED_ON 0x10 //Record LED @@ -84,6 +93,14 @@ ASUS_HANDLE(tled_set, ASUS_HOTK_PREFIX "TLED"); ASUS_HANDLE(rled_set, ASUS_HOTK_PREFIX "RLED"); /* W1JC */ ASUS_HANDLE(pled_set, ASUS_HOTK_PREFIX "PLED"); /* A7J */ +/* Bluetooth and WLAN + * WLED and BLED are not handled like other XLED, because in some dsdt + * they also control the WLAN/Bluetooth device. + */ +ASUS_HANDLE(wl_switch, ASUS_HOTK_PREFIX "WLED"); +ASUS_HANDLE(bt_switch, ASUS_HOTK_PREFIX "BLED"); +ASUS_HANDLE(wireless_status, ASUS_HOTK_PREFIX "RSTS"); /* All new models */ + /* * This is the main structure, we can use it to store anything interesting * about the hotk device @@ -181,14 +198,32 @@ static int read_acpi_int(acpi_handle handle, const char *method, int *val, return (status == AE_OK) && (out_obj.type == ACPI_TYPE_INTEGER); } +static int read_wireless_status(int mask) { + int status; + + if (!wireless_status_handle) + return (hotk->status & mask) ? 1 : 0; + + if (read_acpi_int(wireless_status_handle, NULL, &status, NULL)) { + return (status & mask) ? 1 : 0; + } else + printk(ASUS_WARNING "Error reading Wireless status\n"); + + return (hotk->status & mask) ? 1 : 0; +} + /* Generic LED functions */ static int read_status(int mask) { + /* There is a special method for both wireless devices */ + if (mask == BT_ON || mask == WL_ON) + return read_wireless_status(mask); + return (hotk->status & mask) ? 1 : 0; } static void write_status(acpi_handle handle, int out, int mask, - int invert) + int invert) { hotk->status = (out) ? (hotk->status | mask) : (hotk->status & ~mask); @@ -292,6 +327,51 @@ static int parse_arg(const char *buf, unsigned long count, int *val) return count; } +static ssize_t store_status(const char *buf, size_t count, + acpi_handle handle, int mask, int invert) +{ + int rv, value; + int out = 0; + + rv = parse_arg(buf, count, &value); + if (rv > 0) + out = value ? 1 : 0; + + write_status(handle, out, mask, invert); + + return rv; +} + +/* + * WLAN + */ +static ssize_t show_wlan(struct device *dev, + struct device_attribute *attr, char *buf) +{ + return sprintf(buf, "%d\n", read_status(WL_ON)); +} + +static ssize_t store_wlan(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + return store_status(buf, count, wl_switch_handle, WL_ON, 0); +} + +/* + * Bluetooth + */ +static ssize_t show_bluetooth(struct device *dev, + struct device_attribute *attr, char *buf) +{ + return sprintf(buf, "%d\n", read_status(BT_ON)); +} + +static ssize_t store_bluetooth(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + return store_status(buf, count, bt_switch_handle, BT_ON, 0); +} + static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) { /* TODO Find a better way to handle events count. */ @@ -322,9 +402,13 @@ static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) } while(0) static ASUS_CREATE_DEVICE_ATTR(infos); +static ASUS_CREATE_DEVICE_ATTR(wlan); +static ASUS_CREATE_DEVICE_ATTR(bluetooth); static struct attribute *asuspf_attributes[] = { &dev_attr_infos.attr, + &dev_attr_wlan.attr, + &dev_attr_bluetooth.attr, NULL }; @@ -345,6 +429,13 @@ static struct platform_device *asuspf_device; static void asus_hotk_add_fs(void) { ASUS_SET_DEVICE_ATTR(infos, 0444, show_infos, NULL); + + if (wl_switch_handle) + ASUS_SET_DEVICE_ATTR(wlan, 0644, show_wlan, store_wlan); + + if (bt_switch_handle) + ASUS_SET_DEVICE_ATTR(bluetooth, 0644, + show_bluetooth, store_bluetooth); } static int asus_handle_init(char *name, acpi_handle *handle, @@ -377,7 +468,7 @@ static int asus_hotk_get_info(void) struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; struct acpi_buffer dsdt = { ACPI_ALLOCATE_BUFFER, NULL }; union acpi_object *model = NULL; - int bsts_result; + int bsts_result, hwrs_result; char *string = NULL; acpi_status status; @@ -440,6 +531,22 @@ static int asus_hotk_get_info(void) ASUS_HANDLE_INIT(rled_set); ASUS_HANDLE_INIT(pled_set); + /* + * The HWRS method return informations about the hardware. + * 0x80 bit is for WLAN, 0x100 for Bluetooth. + * The significance of others is yet to be found. + * If we don't find the method, we assume the device are present. + */ + if (!read_acpi_int(hotk->handle, "HRWS", &hwrs_result, NULL)) + hwrs_result = WL_HWRS | BT_HWRS; + + if(hwrs_result & WL_HWRS) + ASUS_HANDLE_INIT(wl_switch); + if(hwrs_result & BT_HWRS) + ASUS_HANDLE_INIT(bt_switch); + + ASUS_HANDLE_INIT(wireless_status); + kfree(model); return AE_OK; @@ -504,6 +611,10 @@ static int asus_hotk_add(struct acpi_device *device) asus_hotk_found = 1; + /* WLED and BLED are on by default */ + write_status(bt_switch_handle, 1, BT_ON, 0); + write_status(wl_switch_handle, 1, WL_ON, 0); + end: if (result) { kfree(hotk->name); -- cgit v0.10.2 From 6b7091e74fe176da97917ca60524e2b3554305f0 Mon Sep 17 00:00:00 2001 From: Corentin Chary Date: Fri, 26 Jan 2007 14:04:45 +0100 Subject: asus-laptop: add backlight support Adds backlight support using backlight class. We now change the brightness *and toggle the backlight !* via /sys/class/backlight/asus-laptop/. If the user switchs the backlight using the keyboard, asus_hotk_notify looks for ATKD_LCD_OFF and ATKD_LCD_ON events, and stores the right state into hotk->status and bd->props->power . Signed-off-by: Corentin Chary Signed-off-by: Len Brown diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig index 87e1db8..89bba27 100644 --- a/drivers/misc/Kconfig +++ b/drivers/misc/Kconfig @@ -75,6 +75,7 @@ config ASUS_LAPTOP depends on ACPI depends on EXPERIMENTAL && !ACPI_ASUS depends on LEDS_CLASS + depends on BACKLIGHT_CLASS_DEVICE ---help--- This is the new Linux driver for Asus laptops. It may also support some MEDION, JVC or VICTOR laptops. It makes all the extra buttons generate diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index 222d4fb..58ab44d 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -40,6 +40,8 @@ #include #include #include +#include +#include #include #include #include @@ -56,6 +58,14 @@ #define ASUS_HOTK_PREFIX "\\_SB.ATKD." /* + * Some events we use, same for all Asus + */ +#define ATKD_BR_UP 0x10 +#define ATKD_BR_DOWN 0x20 +#define ATKD_LCD_ON 0x33 +#define ATKD_LCD_OFF 0x34 + +/* * Known bits returned by \_SB.ATKD.HWRS */ #define WL_HWRS 0x80 @@ -71,6 +81,7 @@ #define TLED_ON 0x08 //touchpad LED #define RLED_ON 0x10 //Record LED #define PLED_ON 0x20 //Phone LED +#define LCD_ON 0x40 //LCD backlight #define ASUS_LOG ASUS_HOTK_FILE ": " #define ASUS_ERR KERN_ERR ASUS_LOG @@ -101,6 +112,19 @@ ASUS_HANDLE(wl_switch, ASUS_HOTK_PREFIX "WLED"); ASUS_HANDLE(bt_switch, ASUS_HOTK_PREFIX "BLED"); ASUS_HANDLE(wireless_status, ASUS_HOTK_PREFIX "RSTS"); /* All new models */ +/* Brightness */ +ASUS_HANDLE(brightness_set, ASUS_HOTK_PREFIX "SPLV"); +ASUS_HANDLE(brightness_get, ASUS_HOTK_PREFIX "GPLV"); + +/* Backlight */ +ASUS_HANDLE(lcd_switch, "\\_SB.PCI0.SBRG.EC0._Q10", /* All new models */ + "\\_SB.PCI0.ISA.EC0._Q10", /* A1x */ + "\\_SB.PCI0.PX40.ECD0._Q10", /* L3C */ + "\\_SB.PCI0.PX40.EC0.Q10", /* M1A */ + "\\_SB.PCI0.LPCB.EC0._Q10", /* P30 */ + "\\_SB.PCI0.PX40.Q10", /* S1x */ + "\\Q10"); /* A2x, L2D, L3D, M2E */ + /* * This is the main structure, we can use it to store anything interesting * about the hotk device @@ -138,6 +162,21 @@ static struct acpi_driver asus_hotk_driver = { }, }; +/* The backlight device /sys/class/backlight */ +static struct backlight_device *asus_backlight_device; + +/* + * The backlight class declaration + */ +static int read_brightness(struct backlight_device *bd); +static int update_bl_status(struct backlight_device *bd); +static struct backlight_properties asusbl_data = { + .owner = THIS_MODULE, + .get_brightness = read_brightness, + .update_status = update_bl_status, + .max_brightness = 15, +}; + /* These functions actually update the LED's, and are called from a * workqueue. By doing this as separate work rather than when the LED * subsystem asks, we avoid messing with the Asus ACPI stuff during a @@ -253,6 +292,86 @@ ASUS_LED_HANDLER(pled, PLED_ON, 0); ASUS_LED_HANDLER(rled, RLED_ON, 0); ASUS_LED_HANDLER(tled, TLED_ON, 0); +static int get_lcd_state(void) +{ + return read_status(LCD_ON); +} + +static int set_lcd_state(int value) +{ + int lcd = 0; + acpi_status status = 0; + + lcd = value ? 1 : 0; + + if (lcd == get_lcd_state()) + return 0; + + if(lcd_switch_handle) { + status = acpi_evaluate_object(lcd_switch_handle, + NULL, NULL, NULL); + + if (ACPI_FAILURE(status)) + printk(ASUS_WARNING "Error switching LCD\n"); + } + + write_status(NULL, lcd, LCD_ON, 0); + return 0; +} + +static void lcd_blank(int blank) +{ + struct backlight_device *bd = asus_backlight_device; + + if(bd) { + down(&bd->sem); + if(likely(bd->props)) { + bd->props->power = blank; + if(likely(bd->props->update_status)) + bd->props->update_status(bd); + } + up(&bd->sem); + } +} + +static int read_brightness(struct backlight_device *bd) +{ + int value; + + if (!read_acpi_int(brightness_get_handle, NULL, &value, NULL)) + printk(ASUS_WARNING "Error reading brightness\n"); + + return value; +} + +static int set_brightness(struct backlight_device *bd, int value) +{ + int ret = 0; + + value = (0 < value) ? ((15 < value) ? 15 : value) : 0; + /* 0 <= value <= 15 */ + + if (!write_acpi_int(brightness_set_handle, NULL, value, NULL)) { + printk(ASUS_WARNING "Error changing brightness\n"); + ret = -EIO; + } + + return ret; +} + +static int update_bl_status(struct backlight_device *bd) +{ + int rv; + int value = bd->props->brightness; + + rv = set_brightness(bd, value); + if(rv) + return rv; + + value = (bd->props->power == FB_BLANK_UNBLANK) ? 1 : 0; + return set_lcd_state(value); +} + /* * Platform device handlers */ @@ -378,6 +497,18 @@ static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) if (!hotk) return; + /* + * We need to tell the backlight device when the backlight power is + * switched + */ + if (event == ATKD_LCD_ON) { + write_status(NULL, 1, LCD_ON, 0); + lcd_blank(FB_BLANK_UNBLANK); + } else if(event == ATKD_LCD_OFF) { + write_status(NULL, 0, LCD_ON, 0); + lcd_blank(FB_BLANK_POWERDOWN); + } + acpi_bus_generate_event(hotk->device, event, hotk->event_count[event % 128]++); @@ -547,6 +678,11 @@ static int asus_hotk_get_info(void) ASUS_HANDLE_INIT(wireless_status); + ASUS_HANDLE_INIT(brightness_set); + ASUS_HANDLE_INIT(brightness_get); + + ASUS_HANDLE_INIT(lcd_switch); + kfree(model); return AE_OK; @@ -611,10 +747,13 @@ static int asus_hotk_add(struct acpi_device *device) asus_hotk_found = 1; - /* WLED and BLED are on by default */ + /* WLED and BLED are on by default */ write_status(bt_switch_handle, 1, BT_ON, 0); write_status(wl_switch_handle, 1, WL_ON, 0); + /* LCD Backlight is on by default */ + write_status(NULL, 1, LCD_ON, 0); + end: if (result) { kfree(hotk->name); @@ -642,6 +781,12 @@ static int asus_hotk_remove(struct acpi_device *device, int type) return 0; } +static void asus_backlight_exit(void) +{ + if(asus_backlight_device) + backlight_device_unregister(asus_backlight_device); +} + #define ASUS_LED_UNREGISTER(object) \ if(object##_led.class_dev \ && !IS_ERR(object##_led.class_dev)) \ @@ -659,6 +804,7 @@ static void asus_led_exit(void) static void __exit asus_laptop_exit(void) { + asus_backlight_exit(); asus_led_exit(); acpi_bus_unregister_driver(&asus_hotk_driver); @@ -669,6 +815,34 @@ static void __exit asus_laptop_exit(void) kfree(asus_info); } +static int asus_backlight_init(struct device * dev) +{ + struct backlight_device *bd; + + if(brightness_set_handle && lcd_switch_handle) { + bd = backlight_device_register (ASUS_HOTK_FILE, dev, + NULL, &asusbl_data); + if (IS_ERR (bd)) { + printk(ASUS_ERR + "Could not register asus backlight device\n"); + asus_backlight_device = NULL; + return PTR_ERR(bd); + } + + asus_backlight_device = bd; + + down(&bd->sem); + if(likely(bd->props)) { + bd->props->brightness = read_brightness(NULL); + bd->props->power = FB_BLANK_UNBLANK; + if(likely(bd->props->update_status)) + bd->props->update_status(bd); + } + up(&bd->sem); + } + return 0; +} + static int asus_led_register(acpi_handle handle, struct led_classdev * ldev, struct device * dev) @@ -739,6 +913,10 @@ static int __init asus_laptop_init(void) dev = acpi_get_physical_device(hotk->device->handle); + result = asus_backlight_init(dev); + if(result) + goto fail_backlight; + result = asus_led_init(dev); if(result) goto fail_led; @@ -778,6 +956,9 @@ fail_platform_driver: asus_led_exit(); fail_led: + asus_backlight_exit(); + +fail_backlight: return result; } -- cgit v0.10.2 From 78127b4a90469d6973de2837d483f80f3709e6e0 Mon Sep 17 00:00:00 2001 From: Corentin Chary Date: Fri, 26 Jan 2007 14:04:49 +0100 Subject: asus-laptop: add display switching support /sys/.../asus-laptop/display can now be used to switch displays like the old /proc/acpi/asus/disp does Signed-off-by: Corentin Chary Signed-off-by: Len Brown diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index 58ab44d..979daa6 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -125,6 +125,23 @@ ASUS_HANDLE(lcd_switch, "\\_SB.PCI0.SBRG.EC0._Q10", /* All new models */ "\\_SB.PCI0.PX40.Q10", /* S1x */ "\\Q10"); /* A2x, L2D, L3D, M2E */ +/* Display */ +ASUS_HANDLE(display_set, ASUS_HOTK_PREFIX "SDSP"); +ASUS_HANDLE(display_get, + "\\_SB.PCI0.P0P1.VGA.GETD", /* A6B, A6K A6R A7D F3JM L4R M6R A3G + M6A M6V VX-1 V6J V6V W3Z */ + "\\_SB.PCI0.P0P2.VGA.GETD", /* A3E A4K, A4D A4L A6J A7J A8J Z71V M9V + S5A M5A z33A W1Jc W2V */ + "\\_SB.PCI0.P0P3.VGA.GETD", /* A6V A6Q */ + "\\_SB.PCI0.P0PA.VGA.GETD", /* A6T, A6M */ + "\\_SB.PCI0.PCI1.VGAC.NMAP", /* L3C */ + "\\_SB.PCI0.VGA.GETD", /* Z96F */ + "\\ACTD", /* A2D */ + "\\ADVG", /* A4G Z71A W1N W5A W5F M2N M3N M5N M6N S1N S5N */ + "\\DNXT", /* P30 */ + "\\INFB", /* A2H D1 L2D L3D L3H L2E L5D L5C M1A M2E L4L W3V */ + "\\SSTE"); /* A3F A6F A3N A3L M6N W3N W6A */ + /* * This is the main structure, we can use it to store anything interesting * about the hotk device @@ -491,6 +508,60 @@ static ssize_t store_bluetooth(struct device *dev, struct device_attribute *attr return store_status(buf, count, bt_switch_handle, BT_ON, 0); } +/* + * Display + */ +static void set_display(int value) +{ + /* no sanity check needed for now */ + if (!write_acpi_int(display_set_handle, NULL, value, NULL)) + printk(ASUS_WARNING "Error setting display\n"); + return; +} + +static int read_display(void) +{ + int value = 0; + + /* In most of the case, we know how to set the display, but sometime + we can't read it */ + if(display_get_handle) { + if (!read_acpi_int(display_get_handle, NULL, &value, NULL)) + printk(ASUS_WARNING "Error reading display status\n"); + } + + value &= 0x0F; /* needed for some models, shouldn't hurt others */ + + return value; +} +/* + * Now, *this* one could be more user-friendly, but so far, no-one has + * complained. The significance of bits is the same as in store_disp() + */ +static ssize_t show_disp(struct device *dev, + struct device_attribute *attr, char *buf) +{ + return sprintf(buf, "%d\n", read_display()); +} + +/* + * Experimental support for display switching. As of now: 1 should activate + * the LCD output, 2 should do for CRT, 4 for TV-Out and 8 for DVI. + * Any combination (bitwise) of these will suffice. I never actually tested 4 + * displays hooked up simultaneously, so be warned. See the acpi4asus README + * for more info. + */ +static ssize_t store_disp(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + int rv, value; + + rv = parse_arg(buf, count, &value); + if (rv > 0) + set_display(value); + return rv; +} + static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) { /* TODO Find a better way to handle events count. */ @@ -535,11 +606,13 @@ static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) static ASUS_CREATE_DEVICE_ATTR(infos); static ASUS_CREATE_DEVICE_ATTR(wlan); static ASUS_CREATE_DEVICE_ATTR(bluetooth); +static ASUS_CREATE_DEVICE_ATTR(display); static struct attribute *asuspf_attributes[] = { &dev_attr_infos.attr, &dev_attr_wlan.attr, &dev_attr_bluetooth.attr, + &dev_attr_display.attr, NULL }; @@ -567,6 +640,12 @@ static void asus_hotk_add_fs(void) if (bt_switch_handle) ASUS_SET_DEVICE_ATTR(bluetooth, 0644, show_bluetooth, store_bluetooth); + + if (display_set_handle && display_get_handle) + ASUS_SET_DEVICE_ATTR(display, 0644, show_disp, store_disp); + else if(display_set_handle) + ASUS_SET_DEVICE_ATTR(display, 0200, NULL, store_disp); + } static int asus_handle_init(char *name, acpi_handle *handle, @@ -683,6 +762,9 @@ static int asus_hotk_get_info(void) ASUS_HANDLE_INIT(lcd_switch); + ASUS_HANDLE_INIT(display_set); + ASUS_HANDLE_INIT(display_get); + kfree(model); return AE_OK; -- cgit v0.10.2 From 722ad97153015aaf5becba3084565e98e71a2aed Mon Sep 17 00:00:00 2001 From: Corentin Chary Date: Fri, 26 Jan 2007 14:04:55 +0100 Subject: asus-laptop: add ledd support Ledd is a special led ... /sys/.../asus-laptop/ledd works like /proc/acpi/asus/ledd Signed-off-by: Corentin Chary Signed-off-by: Len Brown diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index 979daa6..bd963c6 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -104,6 +104,9 @@ ASUS_HANDLE(tled_set, ASUS_HOTK_PREFIX "TLED"); ASUS_HANDLE(rled_set, ASUS_HOTK_PREFIX "RLED"); /* W1JC */ ASUS_HANDLE(pled_set, ASUS_HOTK_PREFIX "PLED"); /* A7J */ +/* LEDD */ +ASUS_HANDLE(ledd_set, ASUS_HOTK_PREFIX "SLCM"); + /* Bluetooth and WLAN * WLED and BLED are not handled like other XLED, because in some dsdt * they also control the WLAN/Bluetooth device. @@ -151,6 +154,7 @@ struct asus_hotk { struct acpi_device *device; //the device we are in acpi_handle handle; //the handle of the hotk device char status; //status of the hotk, for LEDs, ... + u32 ledd_status; //status of the LED display u16 event_count[128]; //count for each event TODO make this better }; @@ -479,6 +483,30 @@ static ssize_t store_status(const char *buf, size_t count, } /* + * LEDD display + */ +static ssize_t show_ledd(struct device *dev, + struct device_attribute *attr, char *buf) +{ + return sprintf(buf, "0x%08x\n", hotk->ledd_status); +} + +static ssize_t store_ledd(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + int rv, value; + + rv = parse_arg(buf, count, &value); + if (rv > 0) { + if (!write_acpi_int(ledd_set_handle, NULL, value, NULL)) + printk(ASUS_WARNING "LED display write failed\n"); + else + hotk->ledd_status = (u32) value; + } + return rv; +} + +/* * WLAN */ static ssize_t show_wlan(struct device *dev, @@ -607,12 +635,14 @@ static ASUS_CREATE_DEVICE_ATTR(infos); static ASUS_CREATE_DEVICE_ATTR(wlan); static ASUS_CREATE_DEVICE_ATTR(bluetooth); static ASUS_CREATE_DEVICE_ATTR(display); +static ASUS_CREATE_DEVICE_ATTR(ledd); static struct attribute *asuspf_attributes[] = { &dev_attr_infos.attr, &dev_attr_wlan.attr, &dev_attr_bluetooth.attr, &dev_attr_display.attr, + &dev_attr_ledd.attr, NULL }; @@ -646,6 +676,9 @@ static void asus_hotk_add_fs(void) else if(display_set_handle) ASUS_SET_DEVICE_ATTR(display, 0200, NULL, store_disp); + if (ledd_set_handle) + ASUS_SET_DEVICE_ATTR(ledd, 0644, show_ledd, store_ledd); + } static int asus_handle_init(char *name, acpi_handle *handle, @@ -741,6 +774,8 @@ static int asus_hotk_get_info(void) ASUS_HANDLE_INIT(rled_set); ASUS_HANDLE_INIT(pled_set); + ASUS_HANDLE_INIT(ledd_set); + /* * The HWRS method return informations about the hardware. * 0x80 bit is for WLAN, 0x100 for Bluetooth. @@ -836,6 +871,9 @@ static int asus_hotk_add(struct acpi_device *device) /* LCD Backlight is on by default */ write_status(NULL, 1, LCD_ON, 0); + /* LED display is off by default */ + hotk->ledd_status = 0xFFF; + end: if (result) { kfree(hotk->name); -- cgit v0.10.2 From 8b857353237c144113b9bbbf9e0236b3f0e7d315 Mon Sep 17 00:00:00 2001 From: Corentin Chary Date: Fri, 26 Jan 2007 14:04:58 +0100 Subject: asus-laptop: add light sensor support /proc/acpi/asus/lslvl is now /sys/.../asus-laptop/ls_level /proc/acpi/asus/lssw is now /sys/.../asus-laptop/ls_switch nothing else .. Signed-off-by: Corentin Chary Signed-off-by: Len Brown diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index bd963c6..6f72cd5 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -145,6 +145,9 @@ ASUS_HANDLE(display_get, "\\INFB", /* A2H D1 L2D L3D L3H L2E L5D L5C M1A M2E L4L W3V */ "\\SSTE"); /* A3F A6F A3N A3L M6N W3N W6A */ +ASUS_HANDLE(ls_switch, ASUS_HOTK_PREFIX "ALSC"); /* Z71A Z71V */ +ASUS_HANDLE(ls_level, ASUS_HOTK_PREFIX "ALSL"); /* Z71A Z71V */ + /* * This is the main structure, we can use it to store anything interesting * about the hotk device @@ -155,6 +158,8 @@ struct asus_hotk { acpi_handle handle; //the handle of the hotk device char status; //status of the hotk, for LEDs, ... u32 ledd_status; //status of the LED display + u8 light_level; //light sensor level + u8 light_switch; //light sensor switch value u16 event_count[128]; //count for each event TODO make this better }; @@ -590,6 +595,62 @@ static ssize_t store_disp(struct device *dev, struct device_attribute *attr, return rv; } +/* + * Light Sens + */ +static void set_light_sens_switch(int value) +{ + if (!write_acpi_int(ls_switch_handle, NULL, value, NULL)) + printk(ASUS_WARNING "Error setting light sensor switch\n"); + hotk->light_switch = value; +} + +static ssize_t show_lssw(struct device *dev, + struct device_attribute *attr, char *buf) +{ + return sprintf(buf, "%d\n", hotk->light_switch); +} + +static ssize_t store_lssw(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + int rv, value; + + rv = parse_arg(buf, count, &value); + if (rv > 0) + set_light_sens_switch(value ? 1 : 0); + + return rv; +} + +static void set_light_sens_level(int value) +{ + if (!write_acpi_int(ls_level_handle, NULL, value, NULL)) + printk(ASUS_WARNING "Error setting light sensor level\n"); + hotk->light_level = value; +} + +static ssize_t show_lslvl(struct device *dev, + struct device_attribute *attr, char *buf) +{ + return sprintf(buf, "%d\n", hotk->light_level); +} + +static ssize_t store_lslvl(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + int rv, value; + + rv = parse_arg(buf, count, &value); + if (rv > 0) { + value = (0 < value) ? ((15 < value) ? 15 : value) : 0; + /* 0 <= value <= 15 */ + set_light_sens_level(value); + } + + return rv; +} + static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) { /* TODO Find a better way to handle events count. */ @@ -636,6 +697,8 @@ static ASUS_CREATE_DEVICE_ATTR(wlan); static ASUS_CREATE_DEVICE_ATTR(bluetooth); static ASUS_CREATE_DEVICE_ATTR(display); static ASUS_CREATE_DEVICE_ATTR(ledd); +static ASUS_CREATE_DEVICE_ATTR(ls_switch); +static ASUS_CREATE_DEVICE_ATTR(ls_level); static struct attribute *asuspf_attributes[] = { &dev_attr_infos.attr, @@ -643,6 +706,8 @@ static struct attribute *asuspf_attributes[] = { &dev_attr_bluetooth.attr, &dev_attr_display.attr, &dev_attr_ledd.attr, + &dev_attr_ls_switch.attr, + &dev_attr_ls_level.attr, NULL }; @@ -679,6 +744,10 @@ static void asus_hotk_add_fs(void) if (ledd_set_handle) ASUS_SET_DEVICE_ATTR(ledd, 0644, show_ledd, store_ledd); + if (ls_switch_handle && ls_level_handle) { + ASUS_SET_DEVICE_ATTR(ls_level, 0644, show_lslvl, store_lslvl); + ASUS_SET_DEVICE_ATTR(ls_switch, 0644, show_lssw, store_lssw); + } } static int asus_handle_init(char *name, acpi_handle *handle, @@ -800,6 +869,11 @@ static int asus_hotk_get_info(void) ASUS_HANDLE_INIT(display_set); ASUS_HANDLE_INIT(display_get); + /* There is a lot of models with "ALSL", but a few get + a real light sens, so we need to check it. */ + if(ASUS_HANDLE_INIT(ls_switch)) + ASUS_HANDLE_INIT(ls_level); + kfree(model); return AE_OK; @@ -874,6 +948,16 @@ static int asus_hotk_add(struct acpi_device *device) /* LED display is off by default */ hotk->ledd_status = 0xFFF; + /* Set initial values of light sensor and level */ + hotk->light_switch = 1; /* Default to light sensor disabled */ + hotk->light_level = 0; /* level 5 for sensor sensitivity */ + + if (ls_switch_handle) + set_light_sens_switch(hotk->light_switch); + + if (ls_level_handle) + set_light_sens_level(hotk->light_level); + end: if (result) { kfree(hotk->name); -- cgit v0.10.2 From 8def05fa82bfa4af0c8e83a00ff377ddd9074480 Mon Sep 17 00:00:00 2001 From: Len Brown Date: Tue, 30 Jan 2007 01:46:43 -0500 Subject: asus-laptop: Lindent Signed-off-by: Len Brown diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index 6f72cd5..b624350 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -79,9 +79,9 @@ #define BT_ON 0x02 //internal Bluetooth #define MLED_ON 0x04 //mail LED #define TLED_ON 0x08 //touchpad LED -#define RLED_ON 0x10 //Record LED -#define PLED_ON 0x20 //Phone LED -#define LCD_ON 0x40 //LCD backlight +#define RLED_ON 0x10 //Record LED +#define PLED_ON 0x20 //Phone LED +#define LCD_ON 0x40 //LCD backlight #define ASUS_LOG ASUS_HOTK_FILE ": " #define ASUS_ERR KERN_ERR ASUS_LOG @@ -101,8 +101,8 @@ MODULE_LICENSE("GPL"); /* LED */ ASUS_HANDLE(mled_set, ASUS_HOTK_PREFIX "MLED"); ASUS_HANDLE(tled_set, ASUS_HOTK_PREFIX "TLED"); -ASUS_HANDLE(rled_set, ASUS_HOTK_PREFIX "RLED"); /* W1JC */ -ASUS_HANDLE(pled_set, ASUS_HOTK_PREFIX "PLED"); /* A7J */ +ASUS_HANDLE(rled_set, ASUS_HOTK_PREFIX "RLED"); /* W1JC */ +ASUS_HANDLE(pled_set, ASUS_HOTK_PREFIX "PLED"); /* A7J */ /* LEDD */ ASUS_HANDLE(ledd_set, ASUS_HOTK_PREFIX "SLCM"); @@ -113,53 +113,52 @@ ASUS_HANDLE(ledd_set, ASUS_HOTK_PREFIX "SLCM"); */ ASUS_HANDLE(wl_switch, ASUS_HOTK_PREFIX "WLED"); ASUS_HANDLE(bt_switch, ASUS_HOTK_PREFIX "BLED"); -ASUS_HANDLE(wireless_status, ASUS_HOTK_PREFIX "RSTS"); /* All new models */ +ASUS_HANDLE(wireless_status, ASUS_HOTK_PREFIX "RSTS"); /* All new models */ /* Brightness */ ASUS_HANDLE(brightness_set, ASUS_HOTK_PREFIX "SPLV"); ASUS_HANDLE(brightness_get, ASUS_HOTK_PREFIX "GPLV"); /* Backlight */ -ASUS_HANDLE(lcd_switch, "\\_SB.PCI0.SBRG.EC0._Q10", /* All new models */ - "\\_SB.PCI0.ISA.EC0._Q10", /* A1x */ - "\\_SB.PCI0.PX40.ECD0._Q10", /* L3C */ - "\\_SB.PCI0.PX40.EC0.Q10", /* M1A */ - "\\_SB.PCI0.LPCB.EC0._Q10", /* P30 */ - "\\_SB.PCI0.PX40.Q10", /* S1x */ - "\\Q10"); /* A2x, L2D, L3D, M2E */ +ASUS_HANDLE(lcd_switch, "\\_SB.PCI0.SBRG.EC0._Q10", /* All new models */ + "\\_SB.PCI0.ISA.EC0._Q10", /* A1x */ + "\\_SB.PCI0.PX40.ECD0._Q10", /* L3C */ + "\\_SB.PCI0.PX40.EC0.Q10", /* M1A */ + "\\_SB.PCI0.LPCB.EC0._Q10", /* P30 */ + "\\_SB.PCI0.PX40.Q10", /* S1x */ + "\\Q10"); /* A2x, L2D, L3D, M2E */ /* Display */ ASUS_HANDLE(display_set, ASUS_HOTK_PREFIX "SDSP"); -ASUS_HANDLE(display_get, - "\\_SB.PCI0.P0P1.VGA.GETD", /* A6B, A6K A6R A7D F3JM L4R M6R A3G - M6A M6V VX-1 V6J V6V W3Z */ - "\\_SB.PCI0.P0P2.VGA.GETD", /* A3E A4K, A4D A4L A6J A7J A8J Z71V M9V +ASUS_HANDLE(display_get, "\\_SB.PCI0.P0P1.VGA.GETD", /* A6B, A6K A6R A7D F3JM L4R M6R A3G + M6A M6V VX-1 V6J V6V W3Z */ + "\\_SB.PCI0.P0P2.VGA.GETD", /* A3E A4K, A4D A4L A6J A7J A8J Z71V M9V S5A M5A z33A W1Jc W2V */ - "\\_SB.PCI0.P0P3.VGA.GETD", /* A6V A6Q */ - "\\_SB.PCI0.P0PA.VGA.GETD", /* A6T, A6M */ - "\\_SB.PCI0.PCI1.VGAC.NMAP", /* L3C */ - "\\_SB.PCI0.VGA.GETD", /* Z96F */ - "\\ACTD", /* A2D */ - "\\ADVG", /* A4G Z71A W1N W5A W5F M2N M3N M5N M6N S1N S5N */ - "\\DNXT", /* P30 */ - "\\INFB", /* A2H D1 L2D L3D L3H L2E L5D L5C M1A M2E L4L W3V */ - "\\SSTE"); /* A3F A6F A3N A3L M6N W3N W6A */ - -ASUS_HANDLE(ls_switch, ASUS_HOTK_PREFIX "ALSC"); /* Z71A Z71V */ -ASUS_HANDLE(ls_level, ASUS_HOTK_PREFIX "ALSL"); /* Z71A Z71V */ + "\\_SB.PCI0.P0P3.VGA.GETD", /* A6V A6Q */ + "\\_SB.PCI0.P0PA.VGA.GETD", /* A6T, A6M */ + "\\_SB.PCI0.PCI1.VGAC.NMAP", /* L3C */ + "\\_SB.PCI0.VGA.GETD", /* Z96F */ + "\\ACTD", /* A2D */ + "\\ADVG", /* A4G Z71A W1N W5A W5F M2N M3N M5N M6N S1N S5N */ + "\\DNXT", /* P30 */ + "\\INFB", /* A2H D1 L2D L3D L3H L2E L5D L5C M1A M2E L4L W3V */ + "\\SSTE"); /* A3F A6F A3N A3L M6N W3N W6A */ + +ASUS_HANDLE(ls_switch, ASUS_HOTK_PREFIX "ALSC"); /* Z71A Z71V */ +ASUS_HANDLE(ls_level, ASUS_HOTK_PREFIX "ALSL"); /* Z71A Z71V */ /* * This is the main structure, we can use it to store anything interesting * about the hotk device */ struct asus_hotk { - char *name; //laptop name + char *name; //laptop name struct acpi_device *device; //the device we are in acpi_handle handle; //the handle of the hotk device char status; //status of the hotk, for LEDs, ... u32 ledd_status; //status of the LED display - u8 light_level; //light sensor level - u8 light_switch; //light sensor switch value + u8 light_level; //light sensor level + u8 light_switch; //light sensor switch value u16 event_count[128]; //count for each event TODO make this better }; @@ -197,10 +196,10 @@ static struct backlight_device *asus_backlight_device; static int read_brightness(struct backlight_device *bd); static int update_bl_status(struct backlight_device *bd); static struct backlight_properties asusbl_data = { - .owner = THIS_MODULE, - .get_brightness = read_brightness, - .update_status = update_bl_status, - .max_brightness = 15, + .owner = THIS_MODULE, + .get_brightness = read_brightness, + .update_status = update_bl_status, + .max_brightness = 15, }; /* These functions actually update the LED's, and are called from a @@ -263,7 +262,8 @@ static int read_acpi_int(acpi_handle handle, const char *method, int *val, return (status == AE_OK) && (out_obj.type == ACPI_TYPE_INTEGER); } -static int read_wireless_status(int mask) { +static int read_wireless_status(int mask) +{ int status; if (!wireless_status_handle) @@ -287,8 +287,7 @@ static int read_status(int mask) return (hotk->status & mask) ? 1 : 0; } -static void write_status(acpi_handle handle, int out, int mask, - int invert) +static void write_status(acpi_handle handle, int out, int mask, int invert) { hotk->status = (out) ? (hotk->status | mask) : (hotk->status & ~mask); @@ -333,7 +332,7 @@ static int set_lcd_state(int value) if (lcd == get_lcd_state()) return 0; - if(lcd_switch_handle) { + if (lcd_switch_handle) { status = acpi_evaluate_object(lcd_switch_handle, NULL, NULL, NULL); @@ -349,12 +348,12 @@ static void lcd_blank(int blank) { struct backlight_device *bd = asus_backlight_device; - if(bd) { + if (bd) { down(&bd->sem); - if(likely(bd->props)) { + if (likely(bd->props)) { bd->props->power = blank; - if(likely(bd->props->update_status)) - bd->props->update_status(bd); + if (likely(bd->props->update_status)) + bd->props->update_status(bd); } up(&bd->sem); } @@ -391,7 +390,7 @@ static int update_bl_status(struct backlight_device *bd) int value = bd->props->brightness; rv = set_brightness(bd, value); - if(rv) + if (rv) return rv; value = (bd->props->power == FB_BLANK_UNBLANK) ? 1 : 0; @@ -408,7 +407,7 @@ static int update_bl_status(struct backlight_device *bd) * number of bytes written in page */ static ssize_t show_infos(struct device *dev, - struct device_attribute *attr, char *page) + struct device_attribute *attr, char *page) { int len = 0; int temp; @@ -535,8 +534,9 @@ static ssize_t show_bluetooth(struct device *dev, return sprintf(buf, "%d\n", read_status(BT_ON)); } -static ssize_t store_bluetooth(struct device *dev, struct device_attribute *attr, - const char *buf, size_t count) +static ssize_t store_bluetooth(struct device *dev, + struct device_attribute *attr, const char *buf, + size_t count) { return store_status(buf, count, bt_switch_handle, BT_ON, 0); } @@ -558,7 +558,7 @@ static int read_display(void) /* In most of the case, we know how to set the display, but sometime we can't read it */ - if(display_get_handle) { + if (display_get_handle) { if (!read_acpi_int(display_get_handle, NULL, &value, NULL)) printk(ASUS_WARNING "Error reading display status\n"); } @@ -567,6 +567,7 @@ static int read_display(void) return value; } + /* * Now, *this* one could be more user-friendly, but so far, no-one has * complained. The significance of bits is the same as in store_disp() @@ -664,7 +665,7 @@ static void asus_hotk_notify(acpi_handle handle, u32 event, void *data) if (event == ATKD_LCD_ON) { write_status(NULL, 1, LCD_ON, 0); lcd_blank(FB_BLANK_UNBLANK); - } else if(event == ATKD_LCD_OFF) { + } else if (event == ATKD_LCD_OFF) { write_status(NULL, 0, LCD_ON, 0); lcd_blank(FB_BLANK_POWERDOWN); } @@ -701,30 +702,29 @@ static ASUS_CREATE_DEVICE_ATTR(ls_switch); static ASUS_CREATE_DEVICE_ATTR(ls_level); static struct attribute *asuspf_attributes[] = { - &dev_attr_infos.attr, - &dev_attr_wlan.attr, - &dev_attr_bluetooth.attr, - &dev_attr_display.attr, - &dev_attr_ledd.attr, - &dev_attr_ls_switch.attr, - &dev_attr_ls_level.attr, - NULL + &dev_attr_infos.attr, + &dev_attr_wlan.attr, + &dev_attr_bluetooth.attr, + &dev_attr_display.attr, + &dev_attr_ledd.attr, + &dev_attr_ls_switch.attr, + &dev_attr_ls_level.attr, + NULL }; static struct attribute_group asuspf_attribute_group = { - .attrs = asuspf_attributes + .attrs = asuspf_attributes }; static struct platform_driver asuspf_driver = { - .driver = { - .name = ASUS_HOTK_FILE, - .owner = THIS_MODULE, - } + .driver = { + .name = ASUS_HOTK_FILE, + .owner = THIS_MODULE, + } }; static struct platform_device *asuspf_device; - static void asus_hotk_add_fs(void) { ASUS_SET_DEVICE_ATTR(infos, 0444, show_infos, NULL); @@ -738,7 +738,7 @@ static void asus_hotk_add_fs(void) if (display_set_handle && display_get_handle) ASUS_SET_DEVICE_ATTR(display, 0644, show_disp, store_disp); - else if(display_set_handle) + else if (display_set_handle) ASUS_SET_DEVICE_ATTR(display, 0200, NULL, store_disp); if (ledd_set_handle) @@ -750,7 +750,7 @@ static void asus_hotk_add_fs(void) } } -static int asus_handle_init(char *name, acpi_handle *handle, +static int asus_handle_init(char *name, acpi_handle * handle, char **paths, int num_paths) { int i; @@ -770,7 +770,6 @@ static int asus_handle_init(char *name, acpi_handle *handle, asus_handle_init(#object, &object##_handle, object##_paths, \ ARRAY_SIZE(object##_paths)) - /* * This function is used to initialize the hotk with right values. In this * method, we can make all the detection we want, and modify the hotk struct @@ -835,7 +834,7 @@ static int asus_hotk_get_info(void) if (!hotk->name) return -ENOMEM; - if(*string) + if (*string) printk(ASUS_NOTICE " %s model detected\n", string); ASUS_HANDLE_INIT(mled_set); @@ -854,9 +853,9 @@ static int asus_hotk_get_info(void) if (!read_acpi_int(hotk->handle, "HRWS", &hwrs_result, NULL)) hwrs_result = WL_HWRS | BT_HWRS; - if(hwrs_result & WL_HWRS) + if (hwrs_result & WL_HWRS) ASUS_HANDLE_INIT(wl_switch); - if(hwrs_result & BT_HWRS) + if (hwrs_result & BT_HWRS) ASUS_HANDLE_INIT(bt_switch); ASUS_HANDLE_INIT(wireless_status); @@ -871,7 +870,7 @@ static int asus_hotk_get_info(void) /* There is a lot of models with "ALSL", but a few get a real light sens, so we need to check it. */ - if(ASUS_HANDLE_INIT(ls_switch)) + if (ASUS_HANDLE_INIT(ls_switch)) ASUS_HANDLE_INIT(ls_level); kfree(model); @@ -948,15 +947,15 @@ static int asus_hotk_add(struct acpi_device *device) /* LED display is off by default */ hotk->ledd_status = 0xFFF; - /* Set initial values of light sensor and level */ - hotk->light_switch = 1; /* Default to light sensor disabled */ - hotk->light_level = 0; /* level 5 for sensor sensitivity */ + /* Set initial values of light sensor and level */ + hotk->light_switch = 1; /* Default to light sensor disabled */ + hotk->light_level = 0; /* level 5 for sensor sensitivity */ - if (ls_switch_handle) - set_light_sens_switch(hotk->light_switch); + if (ls_switch_handle) + set_light_sens_switch(hotk->light_switch); - if (ls_level_handle) - set_light_sens_level(hotk->light_level); + if (ls_level_handle) + set_light_sens_level(hotk->light_level); end: if (result) { @@ -987,7 +986,7 @@ static int asus_hotk_remove(struct acpi_device *device, int type) static void asus_backlight_exit(void) { - if(asus_backlight_device) + if (asus_backlight_device) backlight_device_unregister(asus_backlight_device); } @@ -1012,21 +1011,21 @@ static void __exit asus_laptop_exit(void) asus_led_exit(); acpi_bus_unregister_driver(&asus_hotk_driver); - sysfs_remove_group(&asuspf_device->dev.kobj, &asuspf_attribute_group); - platform_device_unregister(asuspf_device); - platform_driver_unregister(&asuspf_driver); + sysfs_remove_group(&asuspf_device->dev.kobj, &asuspf_attribute_group); + platform_device_unregister(asuspf_device); + platform_driver_unregister(&asuspf_driver); kfree(asus_info); } -static int asus_backlight_init(struct device * dev) +static int asus_backlight_init(struct device *dev) { struct backlight_device *bd; - if(brightness_set_handle && lcd_switch_handle) { - bd = backlight_device_register (ASUS_HOTK_FILE, dev, - NULL, &asusbl_data); - if (IS_ERR (bd)) { + if (brightness_set_handle && lcd_switch_handle) { + bd = backlight_device_register(ASUS_HOTK_FILE, dev, + NULL, &asusbl_data); + if (IS_ERR(bd)) { printk(ASUS_ERR "Could not register asus backlight device\n"); asus_backlight_device = NULL; @@ -1036,11 +1035,11 @@ static int asus_backlight_init(struct device * dev) asus_backlight_device = bd; down(&bd->sem); - if(likely(bd->props)) { + if (likely(bd->props)) { bd->props->brightness = read_brightness(NULL); bd->props->power = FB_BLANK_UNBLANK; - if(likely(bd->props->update_status)) - bd->props->update_status(bd); + if (likely(bd->props->update_status)) + bd->props->update_status(bd); } up(&bd->sem); } @@ -1048,39 +1047,39 @@ static int asus_backlight_init(struct device * dev) } static int asus_led_register(acpi_handle handle, - struct led_classdev * ldev, - struct device * dev) + struct led_classdev *ldev, struct device *dev) { - if(!handle) + if (!handle) return 0; return led_classdev_register(dev, ldev); } + #define ASUS_LED_REGISTER(object, device) \ asus_led_register(object##_set_handle, &object##_led, device) -static int asus_led_init(struct device * dev) +static int asus_led_init(struct device *dev) { int rv; rv = ASUS_LED_REGISTER(mled, dev); - if(rv) + if (rv) return rv; rv = ASUS_LED_REGISTER(tled, dev); - if(rv) + if (rv) return rv; rv = ASUS_LED_REGISTER(rled, dev); - if(rv) + if (rv) return rv; rv = ASUS_LED_REGISTER(pled, dev); - if(rv) + if (rv) return rv; led_workqueue = create_singlethread_workqueue("led_workqueue"); - if(!led_workqueue) + if (!led_workqueue) return -ENOMEM; return 0; @@ -1118,51 +1117,51 @@ static int __init asus_laptop_init(void) dev = acpi_get_physical_device(hotk->device->handle); result = asus_backlight_init(dev); - if(result) + if (result) goto fail_backlight; result = asus_led_init(dev); - if(result) + if (result) goto fail_led; - /* Register platform stuff */ + /* Register platform stuff */ result = platform_driver_register(&asuspf_driver); - if (result) - goto fail_platform_driver; + if (result) + goto fail_platform_driver; - asuspf_device = platform_device_alloc(ASUS_HOTK_FILE, -1); - if (!asuspf_device) { - result = -ENOMEM; - goto fail_platform_device1; - } + asuspf_device = platform_device_alloc(ASUS_HOTK_FILE, -1); + if (!asuspf_device) { + result = -ENOMEM; + goto fail_platform_device1; + } - result = platform_device_add(asuspf_device); - if (result) - goto fail_platform_device2; + result = platform_device_add(asuspf_device); + if (result) + goto fail_platform_device2; - result = sysfs_create_group(&asuspf_device->dev.kobj, + result = sysfs_create_group(&asuspf_device->dev.kobj, &asuspf_attribute_group); - if (result) - goto fail_sysfs; + if (result) + goto fail_sysfs; - return 0; + return 0; -fail_sysfs: - platform_device_del(asuspf_device); + fail_sysfs: + platform_device_del(asuspf_device); -fail_platform_device2: + fail_platform_device2: platform_device_put(asuspf_device); -fail_platform_device1: - platform_driver_unregister(&asuspf_driver); + fail_platform_device1: + platform_driver_unregister(&asuspf_driver); -fail_platform_driver: + fail_platform_driver: asus_led_exit(); -fail_led: + fail_led: asus_backlight_exit(); -fail_backlight: + fail_backlight: return result; } -- cgit v0.10.2 From 37cabc81640ddba28a2aa7f0d1286a1012eae248 Mon Sep 17 00:00:00 2001 From: "Robert P. J. Day" Date: Sat, 27 Jan 2007 01:55:18 -0500 Subject: ACPI: Correct ACPI_DEBUG_OUTPUT typo -#ifdef CONFIG_ACPI_DEBUG_OUTPUT +#ifdef ACPI_DEBUG_OUTPUT As the former doesn't exist. Signed-off-by: Robert P. J. Day Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 283d875..0bd788a 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -891,7 +891,7 @@ static int acpi_device_set_context(struct acpi_device *device, int type) static void acpi_device_get_debug_info(struct acpi_device *device, acpi_handle handle, int type) { -#ifdef CONFIG_ACPI_DEBUG_OUTPUT +#ifdef ACPI_DEBUG_OUTPUT char *type_string = NULL; char name[80] = { '?', '\0' }; struct acpi_buffer buffer = { sizeof(name), name }; @@ -928,7 +928,7 @@ static void acpi_device_get_debug_info(struct acpi_device *device, } printk(KERN_DEBUG "Found %s %s [%p]\n", type_string, name, handle); -#endif /*CONFIG_ACPI_DEBUG_OUTPUT */ +#endif /* ACPI_DEBUG_OUTPUT */ } static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) -- cgit v0.10.2 From 7ac2735462349ca35d8807d93d66cf4d9ea7b729 Mon Sep 17 00:00:00 2001 From: Len Brown Date: Tue, 30 Jan 2007 02:13:44 -0500 Subject: ACPI: delete unused acpi_device_get_debug_info() Signed-off-by: Len Brown diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 0bd788a..2e0fc8c 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -888,49 +888,6 @@ static int acpi_device_set_context(struct acpi_device *device, int type) return result; } -static void acpi_device_get_debug_info(struct acpi_device *device, - acpi_handle handle, int type) -{ -#ifdef ACPI_DEBUG_OUTPUT - char *type_string = NULL; - char name[80] = { '?', '\0' }; - struct acpi_buffer buffer = { sizeof(name), name }; - - switch (type) { - case ACPI_BUS_TYPE_DEVICE: - type_string = "Device"; - acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); - break; - case ACPI_BUS_TYPE_POWER: - type_string = "Power Resource"; - acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); - break; - case ACPI_BUS_TYPE_PROCESSOR: - type_string = "Processor"; - acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); - break; - case ACPI_BUS_TYPE_SYSTEM: - type_string = "System"; - acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); - break; - case ACPI_BUS_TYPE_THERMAL: - type_string = "Thermal Zone"; - acpi_get_name(handle, ACPI_FULL_PATHNAME, &buffer); - break; - case ACPI_BUS_TYPE_POWER_BUTTON: - type_string = "Power Button"; - sprintf(name, "PWRB"); - break; - case ACPI_BUS_TYPE_SLEEP_BUTTON: - type_string = "Sleep Button"; - sprintf(name, "SLPB"); - break; - } - - printk(KERN_DEBUG "Found %s %s [%p]\n", type_string, name, handle); -#endif /* ACPI_DEBUG_OUTPUT */ -} - static int acpi_bus_remove(struct acpi_device *dev, int rmdevice) { int result = 0; @@ -1076,8 +1033,6 @@ acpi_add_single_object(struct acpi_device **child, if ((result = acpi_device_set_context(device, type))) goto end; - acpi_device_get_debug_info(device, handle, type); - acpi_device_register(device, parent); /* -- cgit v0.10.2 From bfd80223d73f80e1d1c69dace9151756b3ef3b49 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Wed, 31 Jan 2007 16:00:20 -0800 Subject: ACPI: correct id for fixed buttons ACPI_BUTTON_HID_POWERF was changed, but this change was not propogated to button.c, thus breaking detection of fixed power and sleep buttons. Signed-off-by: Alexey Starikovskiy Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/drivers/acpi/button.c b/drivers/acpi/button.c index 5ef885e..7fda02c 100644 --- a/drivers/acpi/button.c +++ b/drivers/acpi/button.c @@ -74,7 +74,7 @@ static int acpi_button_state_open_fs(struct inode *inode, struct file *file); static struct acpi_driver acpi_button_driver = { .name = ACPI_BUTTON_DRIVER_NAME, .class = ACPI_BUTTON_CLASS, - .ids = "ACPI_FPB,ACPI_FSB,PNP0C0D,PNP0C0C,PNP0C0E", + .ids = "button_power,button_sleep,PNP0C0D,PNP0C0C,PNP0C0E", .ops = { .add = acpi_button_add, .remove = acpi_button_remove, -- cgit v0.10.2 From db50342205deabaff9ce1fbe53d5ba351992fa08 Mon Sep 17 00:00:00 2001 From: Len Brown Date: Fri, 2 Feb 2007 21:05:04 -0500 Subject: ACPI: prevent build failure when CONFIG_X86_NUMAQ=y ...by disabling CONFIG_ACPI when CONFIG_X86_NUMAQ=y otherwise arch/i386/pci/Makefile forgets that it needs to build acpi.o drivers/built-in.o: In function `acpi_pci_root_add': pci_root.c:(.text+0x45ec4): undefined reference to `pci_acpi_scan_root' Signed-off-by: Len Brown diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index f4f000a..b61a063 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -3,6 +3,7 @@ # menu "ACPI (Advanced Configuration and Power Interface) Support" + depends on !X86_NUMAQ depends on !X86_VISWS depends on !IA64_HP_SIM depends on IA64 || X86 -- cgit v0.10.2 From c9e3ba2c1d178195e17bb4f1d49c32e0be8dbb16 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Update function header Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evrgnini.c b/drivers/acpi/events/evrgnini.c index 203d135..790d49b 100644 --- a/drivers/acpi/events/evrgnini.c +++ b/drivers/acpi/events/evrgnini.c @@ -432,6 +432,9 @@ acpi_ev_default_region_setup(acpi_handle handle, * a PCI address in the scope of the definition. This address is * required to perform an access to PCI config space. * + * MUTEX: Interpreter should be unlocked, because we may run the _REG + * method for this region. + * ******************************************************************************/ acpi_status -- cgit v0.10.2 From 24058054d781934df526be114c612cf2b29cf4e7 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Handle mis-matched package length Implement support within the AML interpreter for package objects that contain a mismatch between the AML length and package element count. In this case, the lesser of the two is used. Some BIOS code apparently modifies the package length on the fly, and this change supports this. Provides compatibility with the MS AML interpreter. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dsobject.c b/drivers/acpi/dispatcher/dsobject.c index 72190ab..aaeb9f9 100644 --- a/drivers/acpi/dispatcher/dsobject.c +++ b/drivers/acpi/dispatcher/dsobject.c @@ -318,9 +318,7 @@ acpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, obj_desc->package.node = parent->common.node; } - obj_desc->package.count = package_length; - - /* Count the number of items in the package list */ + /* Count the *actual* number of items in the package list */ arg = op->common.value.arg; arg = arg->common.next; @@ -329,11 +327,24 @@ acpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, } /* - * The package length (number of elements) will be the greater - * of the specified length and the length of the initializer list + * The number of elements in the package will be the lesser of the + * specified element count and the length of the initializer list. + * + * Even though the ASL compilers do not allow this to happen (for the + * fixed length package opcode), some BIOS code modifies the AML on the + * fly to adjust the package length, and this code compensates for that. + * This also provides compatibility with other AML interpreters. */ - if (package_list_length > package_length) { - obj_desc->package.count = package_list_length; + obj_desc->package.count = package_length; + + if (package_list_length != package_length) { + ACPI_DEBUG_PRINT((ACPI_DB_INFO, + "Package length mismatch, using lesser of %X(Length Arg) and %X(AML Length)\n", + package_length, package_list_length)); + + if (package_list_length < package_length) { + obj_desc->package.count = package_list_length; + } } /* @@ -356,7 +367,7 @@ acpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, */ arg = op->common.value.arg; arg = arg->common.next; - for (i = 0; arg; i++) { + for (i = 0; i < obj_desc->package.count; i++) { if (arg->common.aml_opcode == AML_INT_RETURN_VALUE_OP) { /* Object (package or buffer) is already built */ -- cgit v0.10.2 From 8f9337c88335846b01801b1047a4caf10527a320 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Handle case NumElements > Package length Additional update for NumElements fix. Must handle case where NumElements > Package list length, pad package with null elements. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dsobject.c b/drivers/acpi/dispatcher/dsobject.c index aaeb9f9..f9f6862b 100644 --- a/drivers/acpi/dispatcher/dsobject.c +++ b/drivers/acpi/dispatcher/dsobject.c @@ -260,7 +260,7 @@ acpi_ds_build_internal_buffer_obj(struct acpi_walk_state *walk_state, } obj_desc->buffer.flags |= AOPOBJ_DATA_VALID; - op->common.node = (struct acpi_namespace_node *)obj_desc; + op->common.node = ACPI_CAST_PTR(struct acpi_namespace_node, obj_desc); return_ACPI_STATUS(AE_OK); } @@ -270,7 +270,8 @@ acpi_ds_build_internal_buffer_obj(struct acpi_walk_state *walk_state, * * PARAMETERS: walk_state - Current walk state * Op - Parser object to be translated - * package_length - Number of elements in the package + * element_count - Number of elements in the package - this is + * the num_elements argument to Package() * obj_desc_ptr - Where the ACPI internal object is returned * * RETURN: Status @@ -278,18 +279,29 @@ acpi_ds_build_internal_buffer_obj(struct acpi_walk_state *walk_state, * DESCRIPTION: Translate a parser Op package object to the equivalent * namespace object * + * NOTE: The number of elements in the package will be always be the num_elements + * count, regardless of the number of elements in the package list. If + * num_elements is smaller, only that many package list elements are used. + * if num_elements is larger, the Package object is padded out with + * objects of type Uninitialized (as per ACPI spec.) + * + * Even though the ASL compilers do not allow num_elements to be smaller + * than the Package list length (for the fixed length package opcode), some + * BIOS code modifies the AML on the fly to adjust the num_elements, and + * this code compensates for that. This also provides compatibility with + * other AML interpreters. + * ******************************************************************************/ acpi_status acpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, union acpi_parse_object *op, - u32 package_length, + u32 element_count, union acpi_operand_object **obj_desc_ptr) { union acpi_parse_object *arg; union acpi_parse_object *parent; union acpi_operand_object *obj_desc = NULL; - u32 package_list_length; acpi_status status = AE_OK; acpi_native_uint i; @@ -318,43 +330,13 @@ acpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, obj_desc->package.node = parent->common.node; } - /* Count the *actual* number of items in the package list */ - - arg = op->common.value.arg; - arg = arg->common.next; - for (package_list_length = 0; arg; package_list_length++) { - arg = arg->common.next; - } - - /* - * The number of elements in the package will be the lesser of the - * specified element count and the length of the initializer list. - * - * Even though the ASL compilers do not allow this to happen (for the - * fixed length package opcode), some BIOS code modifies the AML on the - * fly to adjust the package length, and this code compensates for that. - * This also provides compatibility with other AML interpreters. - */ - obj_desc->package.count = package_length; - - if (package_list_length != package_length) { - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Package length mismatch, using lesser of %X(Length Arg) and %X(AML Length)\n", - package_length, package_list_length)); - - if (package_list_length < package_length) { - obj_desc->package.count = package_list_length; - } - } - /* - * Allocate the pointer array (array of pointers to the - * individual objects). Add an extra pointer slot so - * that the list is always null terminated. + * Allocate the element array (array of pointers to the individual + * objects) based on the num_elements parameter. Add an extra pointer slot + * so that the list is always null terminated. */ obj_desc->package.elements = ACPI_ALLOCATE_ZEROED(((acpi_size) - obj_desc->package. - count + + element_count + 1) * sizeof(void *)); if (!obj_desc->package.elements) { @@ -362,15 +344,20 @@ acpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, return_ACPI_STATUS(AE_NO_MEMORY); } + obj_desc->package.count = element_count; + /* - * Initialize all elements of the package + * Initialize the elements of the package, up to the num_elements count. + * Package is automatically padded with uninitialized (NULL) elements + * if num_elements is greater than the package list length. Likewise, + * Package is truncated if num_elements is less than the list length. */ arg = op->common.value.arg; arg = arg->common.next; - for (i = 0; i < obj_desc->package.count; i++) { + for (i = 0; arg && (i < element_count); i++) { if (arg->common.aml_opcode == AML_INT_RETURN_VALUE_OP) { - /* Object (package or buffer) is already built */ + /* This package element is already built, just get it */ obj_desc->package.elements[i] = ACPI_CAST_PTR(union acpi_operand_object, @@ -384,8 +371,14 @@ acpi_ds_build_internal_package_obj(struct acpi_walk_state *walk_state, arg = arg->common.next; } + if (!arg) { + ACPI_DEBUG_PRINT((ACPI_DB_INFO, + "Package List length larger than NumElements count (%X), truncated\n", + element_count)); + } + obj_desc->package.flags |= AOPOBJ_DATA_VALID; - op->common.node = (struct acpi_namespace_node *)obj_desc; + op->common.node = ACPI_CAST_PTR(struct acpi_namespace_node, obj_desc); return_ACPI_STATUS(status); } @@ -499,8 +492,9 @@ acpi_ds_init_object_from_op(struct acpi_walk_state *walk_state, /* * Defer evaluation of Buffer term_arg operand */ - obj_desc->buffer.node = (struct acpi_namespace_node *) - walk_state->operands[0]; + obj_desc->buffer.node = + ACPI_CAST_PTR(struct acpi_namespace_node, + walk_state->operands[0]); obj_desc->buffer.aml_start = op->named.data; obj_desc->buffer.aml_length = op->named.length; break; @@ -510,8 +504,9 @@ acpi_ds_init_object_from_op(struct acpi_walk_state *walk_state, /* * Defer evaluation of Package term_arg operand */ - obj_desc->package.node = (struct acpi_namespace_node *) - walk_state->operands[0]; + obj_desc->package.node = + ACPI_CAST_PTR(struct acpi_namespace_node, + walk_state->operands[0]); obj_desc->package.aml_start = op->named.data; obj_desc->package.aml_length = op->named.length; break; -- cgit v0.10.2 From c81da66608d65dab04730582dfdfcdcab779e2fe Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Delete recursive feature of ACPI Global Lock Completed a new design and implementation for the ACPI Global Lock support. On the OS side, the global lock is now treated as a standard AML mutex. Previously, multiple OS threads could acquire the global lock simultaneously, but this could cause the BIOS to be starved by the lock in cases such as the Embedded Controller driver, where there is a tight coupling between the OS and the BIOS. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index bf63edc..f82b81c 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c @@ -298,19 +298,13 @@ static void ACPI_SYSTEM_XFACE acpi_ev_global_lock_thread(void *context) { acpi_status status; - /* Signal threads that are waiting for the lock */ + /* Signal the thread that is waiting for the lock */ - if (acpi_gbl_global_lock_thread_count) { + /* Send a unit to the semaphore */ - /* Send sufficient units to the semaphore */ - - status = - acpi_os_signal_semaphore(acpi_gbl_global_lock_semaphore, - acpi_gbl_global_lock_thread_count); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, - "Could not signal Global Lock semaphore")); - } + status = acpi_os_signal_semaphore(acpi_gbl_global_lock_semaphore, 1); + if (ACPI_FAILURE(status)) { + ACPI_ERROR((AE_INFO, "Could not signal Global Lock semaphore")); } } @@ -333,7 +327,8 @@ static u32 acpi_ev_global_lock_handler(void *context) u8 acquired = FALSE; /* - * Attempt to get the lock + * Attempt to get the lock. + * * If we don't get it now, it will be marked pending and we will * take another interrupt when it becomes free. */ @@ -341,6 +336,7 @@ static u32 acpi_ev_global_lock_handler(void *context) if (acquired) { /* Got the lock, now wake all threads waiting for it */ + acpi_gbl_global_lock_acquired = TRUE; acpi_ev_global_lock_thread(context); } @@ -399,6 +395,16 @@ acpi_status acpi_ev_init_global_lock_handler(void) * * DESCRIPTION: Attempt to gain ownership of the Global Lock. * + * MUTEX: Interpreter must be locked + * + * Note: The original implementation allowed multiple threads to "acquire" the + * Global Lock, and the OS would hold the lock until the last thread had + * released it. However, this could potentially starve the BIOS out of the + * lock, especially in the case where there is a tight handshake between the + * Embedded Controller driver and the BIOS. Therefore, this implementation + * allows only one thread to acquire the HW Global Lock at a time, and makes + * the global lock appear as a standard mutex on the OS side. + * *****************************************************************************/ acpi_status acpi_ev_acquire_global_lock(u16 timeout) @@ -408,27 +414,25 @@ acpi_status acpi_ev_acquire_global_lock(u16 timeout) ACPI_FUNCTION_TRACE(ev_acquire_global_lock); -#ifndef ACPI_APPLICATION - /* Make sure that we actually have a global lock */ - - if (!acpi_gbl_global_lock_present) { - return_ACPI_STATUS(AE_NO_GLOBAL_LOCK); + /* + * Only one thread can acquire the GL at a time, the global_lock_mutex + * enforces this. This interface releases the interpreter if we must wait. + */ + status = acpi_ex_system_wait_mutex(acpi_gbl_global_lock_mutex, timeout); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); } -#endif - - /* One more thread wants the global lock */ - - acpi_gbl_global_lock_thread_count++; /* - * If we (OS side vs. BIOS side) have the hardware lock already, - * we are done + * Make sure that a global lock actually exists. If not, just treat + * the lock as a standard mutex. */ - if (acpi_gbl_global_lock_acquired) { + if (!acpi_gbl_global_lock_present) { + acpi_gbl_global_lock_acquired = TRUE; return_ACPI_STATUS(AE_OK); } - /* We must acquire the actual hardware lock */ + /* Attempt to acquire the actual hardware lock */ ACPI_ACQUIRE_GLOBAL_LOCK(acpi_gbl_common_fACS.global_lock, acquired); if (acquired) { @@ -436,25 +440,24 @@ acpi_status acpi_ev_acquire_global_lock(u16 timeout) /* We got the lock */ ACPI_DEBUG_PRINT((ACPI_DB_EXEC, - "Acquired the HW Global Lock\n")); + "Acquired hardware Global Lock\n")); acpi_gbl_global_lock_acquired = TRUE; return_ACPI_STATUS(AE_OK); } /* - * Did not get the lock. The pending bit was set above, and we must now + * Did not get the lock. The pending bit was set above, and we must now * wait until we get the global lock released interrupt. */ - ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Waiting for the HW Global Lock\n")); + ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Waiting for hardware Global Lock\n")); /* - * Acquire the global lock semaphore first. - * Since this wait will block, we must release the interpreter + * Wait for handshake with the global lock interrupt handler. + * This interface releases the interpreter if we must wait. */ - status = - acpi_ex_system_wait_semaphore(acpi_gbl_global_lock_semaphore, - timeout); + status = acpi_ex_system_wait_semaphore(acpi_gbl_global_lock_semaphore, + ACPI_WAIT_FOREVER); return_ACPI_STATUS(status); } @@ -477,38 +480,40 @@ acpi_status acpi_ev_release_global_lock(void) ACPI_FUNCTION_TRACE(ev_release_global_lock); - if (!acpi_gbl_global_lock_thread_count) { + /* Lock must be acquired */ + + if (!acpi_gbl_global_lock_acquired) { ACPI_WARNING((AE_INFO, - "Cannot release HW Global Lock, it has not been acquired")); + "Cannot release the ACPI Global Lock, it has not been acquired")); return_ACPI_STATUS(AE_NOT_ACQUIRED); } - /* One fewer thread has the global lock */ + if (acpi_gbl_global_lock_present) { - acpi_gbl_global_lock_thread_count--; - if (acpi_gbl_global_lock_thread_count) { + /* Allow any thread to release the lock */ - /* There are still some threads holding the lock, cannot release */ + ACPI_RELEASE_GLOBAL_LOCK(acpi_gbl_common_fACS.global_lock, + pending); - return_ACPI_STATUS(AE_OK); + /* + * If the pending bit was set, we must write GBL_RLS to the control + * register + */ + if (pending) { + status = + acpi_set_register(ACPI_BITREG_GLOBAL_LOCK_RELEASE, + 1, ACPI_MTX_LOCK); + } + + ACPI_DEBUG_PRINT((ACPI_DB_EXEC, + "Released hardware Global Lock\n")); } - /* - * No more threads holding lock, we can do the actual hardware - * release - */ - ACPI_RELEASE_GLOBAL_LOCK(acpi_gbl_common_fACS.global_lock, pending); acpi_gbl_global_lock_acquired = FALSE; - /* - * If the pending bit was set, we must write GBL_RLS to the control - * register - */ - if (pending) { - status = acpi_set_register(ACPI_BITREG_GLOBAL_LOCK_RELEASE, - 1, ACPI_MTX_LOCK); - } + /* Release the local GL mutex */ + acpi_os_release_mutex(acpi_gbl_global_lock_mutex); return_ACPI_STATUS(status); } diff --git a/drivers/acpi/executer/exmutex.c b/drivers/acpi/executer/exmutex.c index bf90f04..f1dd1b0 100644 --- a/drivers/acpi/executer/exmutex.c +++ b/drivers/acpi/executer/exmutex.c @@ -44,6 +44,7 @@ #include #include +#include #define _COMPONENT ACPI_EXECUTER ACPI_MODULE_NAME("exmutex") @@ -150,7 +151,7 @@ acpi_ex_acquire_mutex(union acpi_operand_object *time_desc, return_ACPI_STATUS(AE_BAD_PARAMETER); } - /* Sanity check -- we must have a valid thread ID */ + /* Sanity check: we must have a valid thread ID */ if (!walk_state->thread) { ACPI_ERROR((AE_INFO, @@ -174,24 +175,28 @@ acpi_ex_acquire_mutex(union acpi_operand_object *time_desc, /* Support for multiple acquires by the owning thread */ if (obj_desc->mutex.owner_thread) { - - /* Special case for Global Lock, allow all threads */ - - if ((obj_desc->mutex.owner_thread->thread_id == - walk_state->thread->thread_id) || - (obj_desc->mutex.os_mutex == ACPI_GLOBAL_LOCK)) { + if (obj_desc->mutex.owner_thread->thread_id == + walk_state->thread->thread_id) { /* - * The mutex is already owned by this thread, - * just increment the acquisition depth + * The mutex is already owned by this thread, just increment the + * acquisition depth */ obj_desc->mutex.acquisition_depth++; return_ACPI_STATUS(AE_OK); } } - /* Acquire the mutex, wait if necessary */ + /* Acquire the mutex, wait if necessary. Special case for Global Lock */ + + if (obj_desc->mutex.os_mutex == acpi_gbl_global_lock_mutex) { + status = + acpi_ev_acquire_global_lock((u16) time_desc->integer.value); + } else { + status = acpi_ex_system_wait_mutex(obj_desc->mutex.os_mutex, + (u16) time_desc->integer. + value); + } - status = acpi_ex_system_acquire_mutex(time_desc, obj_desc); if (ACPI_FAILURE(status)) { /* Includes failure from a timeout on time_desc */ @@ -211,7 +216,6 @@ acpi_ex_acquire_mutex(union acpi_operand_object *time_desc, /* Link the mutex to the current thread for force-unlock at method exit */ acpi_ex_link_mutex(obj_desc, walk_state->thread); - return_ACPI_STATUS(AE_OK); } @@ -232,7 +236,7 @@ acpi_status acpi_ex_release_mutex(union acpi_operand_object *obj_desc, struct acpi_walk_state *walk_state) { - acpi_status status; + acpi_status status = AE_OK; ACPI_FUNCTION_TRACE(ex_release_mutex); @@ -249,7 +253,7 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc, return_ACPI_STATUS(AE_AML_MUTEX_NOT_ACQUIRED); } - /* Sanity check -- we must have a valid thread ID */ + /* Sanity check: we must have a valid thread ID */ if (!walk_state->thread) { ACPI_ERROR((AE_INFO, @@ -264,7 +268,7 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc, */ if ((obj_desc->mutex.owner_thread->thread_id != walk_state->thread->thread_id) - && (obj_desc->mutex.os_mutex != ACPI_GLOBAL_LOCK)) { + && (obj_desc->mutex.os_mutex != acpi_gbl_global_lock_mutex)) { ACPI_ERROR((AE_INFO, "Thread %lX cannot release Mutex [%4.4s] acquired by thread %lX", (unsigned long)walk_state->thread->thread_id, @@ -274,8 +278,8 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc, } /* - * The sync level of the mutex must be less than or - * equal to the current sync level + * The sync level of the mutex must be less than or equal to the current + * sync level */ if (obj_desc->mutex.sync_level > walk_state->thread->current_sync_level) { ACPI_ERROR((AE_INFO, @@ -298,11 +302,15 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc, acpi_ex_unlink_mutex(obj_desc); - /* Release the mutex */ + /* Release the mutex, special case for Global Lock */ - status = acpi_ex_system_release_mutex(obj_desc); + if (obj_desc->mutex.os_mutex == acpi_gbl_global_lock_mutex) { + status = acpi_ev_release_global_lock(); + } else { + acpi_os_release_mutex(obj_desc->mutex.os_mutex); + } - /* Update the mutex and walk state, restore sync_level before acquire */ + /* Update the mutex and restore sync_level */ obj_desc->mutex.owner_thread = NULL; walk_state->thread->current_sync_level = @@ -326,34 +334,38 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc, void acpi_ex_release_all_mutexes(struct acpi_thread_state *thread) { union acpi_operand_object *next = thread->acquired_mutex_list; - union acpi_operand_object *this; - acpi_status status; + union acpi_operand_object *obj_desc; ACPI_FUNCTION_ENTRY(); /* Traverse the list of owned mutexes, releasing each one */ while (next) { - this = next; - next = this->mutex.next; + obj_desc = next; + next = obj_desc->mutex.next; + + obj_desc->mutex.prev = NULL; + obj_desc->mutex.next = NULL; + obj_desc->mutex.acquisition_depth = 1; + + /* Release the mutex, special case for Global Lock */ - this->mutex.acquisition_depth = 1; - this->mutex.prev = NULL; - this->mutex.next = NULL; + if (obj_desc->mutex.os_mutex == acpi_gbl_global_lock_mutex) { - /* Release the mutex */ + /* Ignore errors */ - status = acpi_ex_system_release_mutex(this); - if (ACPI_FAILURE(status)) { - continue; + (void)acpi_ev_release_global_lock(); + } else { + acpi_os_release_mutex(obj_desc->mutex.os_mutex); } /* Mark mutex unowned */ - this->mutex.owner_thread = NULL; + obj_desc->mutex.owner_thread = NULL; /* Update Thread sync_level (Last mutex is the important one) */ - thread->current_sync_level = this->mutex.original_sync_level; + thread->current_sync_level = + obj_desc->mutex.original_sync_level; } } diff --git a/drivers/acpi/executer/exsystem.c b/drivers/acpi/executer/exsystem.c index 28aef3e..3b9736a 100644 --- a/drivers/acpi/executer/exsystem.c +++ b/drivers/acpi/executer/exsystem.c @@ -227,82 +227,6 @@ acpi_status acpi_ex_system_do_suspend(acpi_integer how_long) /******************************************************************************* * - * FUNCTION: acpi_ex_system_acquire_mutex - * - * PARAMETERS: time_desc - Maximum time to wait for the mutex - * obj_desc - The object descriptor for this op - * - * RETURN: Status - * - * DESCRIPTION: Provides an access point to perform synchronization operations - * within the AML. This function will cause a lock to be generated - * for the Mutex pointed to by obj_desc. - * - ******************************************************************************/ - -acpi_status -acpi_ex_system_acquire_mutex(union acpi_operand_object * time_desc, - union acpi_operand_object * obj_desc) -{ - acpi_status status = AE_OK; - - ACPI_FUNCTION_TRACE_PTR(ex_system_acquire_mutex, obj_desc); - - if (!obj_desc) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - /* Support for the _GL_ Mutex object -- go get the global lock */ - - if (obj_desc->mutex.os_mutex == ACPI_GLOBAL_LOCK) { - status = - acpi_ev_acquire_global_lock((u16) time_desc->integer.value); - return_ACPI_STATUS(status); - } - - status = acpi_ex_system_wait_mutex(obj_desc->mutex.os_mutex, - (u16) time_desc->integer.value); - return_ACPI_STATUS(status); -} - -/******************************************************************************* - * - * FUNCTION: acpi_ex_system_release_mutex - * - * PARAMETERS: obj_desc - The object descriptor for this op - * - * RETURN: Status - * - * DESCRIPTION: Provides an access point to perform synchronization operations - * within the AML. This operation is a request to release a - * previously acquired Mutex. If the Mutex variable is set then - * it will be decremented. - * - ******************************************************************************/ - -acpi_status acpi_ex_system_release_mutex(union acpi_operand_object *obj_desc) -{ - acpi_status status = AE_OK; - - ACPI_FUNCTION_TRACE(ex_system_release_mutex); - - if (!obj_desc) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - /* Support for the _GL_ Mutex object -- release the global lock */ - - if (obj_desc->mutex.os_mutex == ACPI_GLOBAL_LOCK) { - status = acpi_ev_release_global_lock(); - return_ACPI_STATUS(status); - } - - acpi_os_release_mutex(obj_desc->mutex.os_mutex); - return_ACPI_STATUS(AE_OK); -} - -/******************************************************************************* - * * FUNCTION: acpi_ex_system_signal_event * * PARAMETERS: obj_desc - The object descriptor for this op @@ -314,7 +238,7 @@ acpi_status acpi_ex_system_release_mutex(union acpi_operand_object *obj_desc) * ******************************************************************************/ -acpi_status acpi_ex_system_signal_event(union acpi_operand_object *obj_desc) +acpi_status acpi_ex_system_signal_event(union acpi_operand_object * obj_desc) { acpi_status status = AE_OK; diff --git a/drivers/acpi/namespace/nsaccess.c b/drivers/acpi/namespace/nsaccess.c index c1c6c23..b2ef673 100644 --- a/drivers/acpi/namespace/nsaccess.c +++ b/drivers/acpi/namespace/nsaccess.c @@ -195,31 +195,27 @@ acpi_status acpi_ns_root_initialize(void) obj_desc->mutex.sync_level = (u8) (ACPI_TO_INTEGER(val) - 1); - if (ACPI_STRCMP(init_val->name, "_GL_") == 0) { - - /* Create a counting semaphore for the global lock */ + /* Create a mutex */ + + status = + acpi_os_create_mutex(&obj_desc->mutex. + os_mutex); + if (ACPI_FAILURE(status)) { + acpi_ut_remove_reference(obj_desc); + goto unlock_and_exit; + } - status = - acpi_os_create_semaphore - (ACPI_NO_UNIT_LIMIT, 1, - &acpi_gbl_global_lock_semaphore); - if (ACPI_FAILURE(status)) { - acpi_ut_remove_reference - (obj_desc); - goto unlock_and_exit; - } + /* Special case for ACPI Global Lock */ - /* Mark this mutex as very special */ + if (ACPI_STRCMP(init_val->name, "_GL_") == 0) { + acpi_gbl_global_lock_mutex = + obj_desc->mutex.os_mutex; - obj_desc->mutex.os_mutex = - ACPI_GLOBAL_LOCK; - } else { - /* Create a mutex */ + /* Create additional counting semaphore for global lock */ status = - acpi_os_create_mutex(&obj_desc-> - mutex. - os_mutex); + acpi_os_create_semaphore(1, 1, + &acpi_gbl_global_lock_semaphore); if (ACPI_FAILURE(status)) { acpi_ut_remove_reference (obj_desc); diff --git a/drivers/acpi/utilities/utdelete.c b/drivers/acpi/utilities/utdelete.c index 9d3f114..af8e65f 100644 --- a/drivers/acpi/utilities/utdelete.c +++ b/drivers/acpi/utilities/utdelete.c @@ -158,16 +158,20 @@ static void acpi_ut_delete_internal_obj(union acpi_operand_object *object) "***** Mutex %p, OS Mutex %p\n", object, object->mutex.os_mutex)); - if (object->mutex.os_mutex != ACPI_GLOBAL_LOCK) { - acpi_ex_unlink_mutex(object); - acpi_os_delete_mutex(object->mutex.os_mutex); - } else { - /* Global Lock "mutex" is actually a counting semaphore */ + if (object->mutex.os_mutex == acpi_gbl_global_lock_mutex) { + + /* Global Lock has extra semaphore */ (void) acpi_os_delete_semaphore (acpi_gbl_global_lock_semaphore); acpi_gbl_global_lock_semaphore = NULL; + + acpi_os_delete_mutex(object->mutex.os_mutex); + acpi_gbl_global_lock_mutex = NULL; + } else { + acpi_ex_unlink_mutex(object); + acpi_os_delete_mutex(object->mutex.os_mutex); } break; diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 014030a..1038452 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -795,8 +795,8 @@ void acpi_ut_init_globals(void) /* Global Lock support */ acpi_gbl_global_lock_semaphore = NULL; + acpi_gbl_global_lock_mutex = NULL; acpi_gbl_global_lock_acquired = FALSE; - acpi_gbl_global_lock_thread_count = 0; acpi_gbl_global_lock_handle = 0; /* Miscellaneous variables */ diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index 06972e6..bf43184 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -197,6 +197,7 @@ ACPI_EXTERN struct acpi_mutex_info acpi_gbl_mutex_info[ACPI_NUM_MUTEX]; /* * Global lock semaphore works in conjunction with the actual HW global lock */ +ACPI_EXTERN acpi_mutex acpi_gbl_global_lock_mutex; ACPI_EXTERN acpi_semaphore acpi_gbl_global_lock_semaphore; /* @@ -240,7 +241,6 @@ ACPI_EXTERN struct acpi_walk_state *acpi_gbl_breakpoint_walk; /* Misc */ -ACPI_EXTERN u32 acpi_gbl_global_lock_thread_count; ACPI_EXTERN u32 acpi_gbl_original_mode; ACPI_EXTERN u32 acpi_gbl_rsdp_original_location; ACPI_EXTERN u32 acpi_gbl_ns_lookup_count; diff --git a/include/acpi/acinterp.h b/include/acpi/acinterp.h index 91586d0..f266b38 100644 --- a/include/acpi/acinterp.h +++ b/include/acpi/acinterp.h @@ -277,12 +277,6 @@ acpi_status acpi_ex_system_do_suspend(acpi_integer time); acpi_status acpi_ex_system_do_stall(u32 time); -acpi_status -acpi_ex_system_acquire_mutex(union acpi_operand_object *time, - union acpi_operand_object *obj_desc); - -acpi_status acpi_ex_system_release_mutex(union acpi_operand_object *obj_desc); - acpi_status acpi_ex_system_signal_event(union acpi_operand_object *obj_desc); acpi_status diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index 063c4b5..d542140 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -51,7 +51,6 @@ #define ACPI_SERIALIZED 0xFF typedef u32 acpi_mutex_handle; -#define ACPI_GLOBAL_LOCK (acpi_semaphore) (-1) /* Total number of aml opcodes defined */ -- cgit v0.10.2 From a72d47563bce9542b9a83521a4e8175076278ee9 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Release global lock from interrupt handler The ACPI Global Lock interrupt handler no longer queues the execution of a separate thread to signal the global lock semaphore. Instead, the semaphore is signaled directly from the interrupt handler. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index f82b81c..00f33ed 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c @@ -67,8 +67,6 @@ static const char *acpi_notify_value_names[] = { static void ACPI_SYSTEM_XFACE acpi_ev_notify_dispatch(void *context); -static void ACPI_SYSTEM_XFACE acpi_ev_global_lock_thread(void *context); - static u32 acpi_ev_global_lock_handler(void *context); /******************************************************************************* @@ -282,43 +280,19 @@ static void ACPI_SYSTEM_XFACE acpi_ev_notify_dispatch(void *context) /******************************************************************************* * - * FUNCTION: acpi_ev_global_lock_thread - * - * PARAMETERS: Context - From thread interface, not used - * - * RETURN: None - * - * DESCRIPTION: Invoked by SCI interrupt handler upon acquisition of the - * Global Lock. Simply signal all threads that are waiting - * for the lock. - * - ******************************************************************************/ - -static void ACPI_SYSTEM_XFACE acpi_ev_global_lock_thread(void *context) -{ - acpi_status status; - - /* Signal the thread that is waiting for the lock */ - - /* Send a unit to the semaphore */ - - status = acpi_os_signal_semaphore(acpi_gbl_global_lock_semaphore, 1); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, "Could not signal Global Lock semaphore")); - } -} - -/******************************************************************************* - * * FUNCTION: acpi_ev_global_lock_handler * * PARAMETERS: Context - From thread interface, not used * - * RETURN: ACPI_INTERRUPT_HANDLED or ACPI_INTERRUPT_NOT_HANDLED + * RETURN: ACPI_INTERRUPT_HANDLED * * DESCRIPTION: Invoked directly from the SCI handler when a global lock - * release interrupt occurs. Grab the global lock and queue - * the global lock thread for execution + * release interrupt occurs. Attempt to acquire the global lock, + * if successful, signal the thread waiting for the lock. + * + * NOTE: Assumes that the semaphore can be signaled from interrupt level. If + * this is not possible for some reason, a separate thread will have to be + * scheduled to do this. * ******************************************************************************/ @@ -338,7 +312,13 @@ static u32 acpi_ev_global_lock_handler(void *context) /* Got the lock, now wake all threads waiting for it */ acpi_gbl_global_lock_acquired = TRUE; - acpi_ev_global_lock_thread(context); + /* Send a unit to the semaphore */ + + if (ACPI_FAILURE(acpi_os_signal_semaphore( + acpi_gbl_global_lock_semaphore, 1))) { + ACPI_ERROR((AE_INFO, + "Could not signal Global Lock semaphore")); + } } return (ACPI_INTERRUPT_HANDLED); @@ -480,7 +460,7 @@ acpi_status acpi_ev_release_global_lock(void) ACPI_FUNCTION_TRACE(ev_release_global_lock); - /* Lock must be acquired */ + /* Lock must be already acquired */ if (!acpi_gbl_global_lock_acquired) { ACPI_WARNING((AE_INFO, -- cgit v0.10.2 From 0654a6d3c7a777ddccd35c5bbc5765ffbfe3ea96 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Cast acpi_thread_id to UINT32 for debug output only Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/utilities/utdebug.c b/drivers/acpi/utilities/utdebug.c index 9e9054e..8ba8624 100644 --- a/drivers/acpi/utilities/utdebug.c +++ b/drivers/acpi/utilities/utdebug.c @@ -180,9 +180,8 @@ acpi_ut_debug_print(u32 requested_debug_level, if (thread_id != acpi_gbl_prev_thread_id) { if (ACPI_LV_THREADS & acpi_dbg_level) { acpi_os_printf - ("\n**** Context Switch from TID %lX to TID %lX ****\n\n", - (unsigned long) acpi_gbl_prev_thread_id, - (unsigned long) thread_id); + ("\n**** Context Switch from TID %X to TID %X ****\n\n", + (unsigned)acpi_gbl_prev_thread_id, (unsigned)thread_id); } acpi_gbl_prev_thread_id = thread_id; @@ -195,7 +194,7 @@ acpi_ut_debug_print(u32 requested_debug_level, acpi_os_printf("%8s-%04ld ", module_name, line_number); if (ACPI_LV_THREADS & acpi_dbg_level) { - acpi_os_printf("[%04lX] ", thread_id); + acpi_os_printf("[%04X] ", (unsigned)thread_id); } acpi_os_printf("[%02ld] %-22.22s: ", -- cgit v0.10.2 From 6b366e2fe1b68bd9af55caf166eaaf0609ba18a9 Mon Sep 17 00:00:00 2001 From: Fiodor Suietov Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: fix for object premature deletion Fix for object premature deletion after CopyObject on Operation Region (BZ 350) Signed-off-by: Bob Moore Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/utilities/utcopy.c b/drivers/acpi/utilities/utcopy.c index 5e1a80d..5c38276 100644 --- a/drivers/acpi/utilities/utcopy.c +++ b/drivers/acpi/utilities/utcopy.c @@ -719,6 +719,15 @@ acpi_ut_copy_simple_object(union acpi_operand_object *source_desc, acpi_ut_add_reference(source_desc->reference.object); break; + case ACPI_TYPE_REGION: + /* + * We copied the Region Handler, so we now must add a reference + */ + if (dest_desc->region.handler) { + acpi_ut_add_reference(dest_desc->region.handler); + } + break; + default: /* Nothing to do for other simple objects */ break; -- cgit v0.10.2 From 9c52657a2ac8aac5149e11049497b10918e1f58f Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Temporary fix for BankValue parameter Temporary fix for BankValue parameter of a Bank Field to support all constant values, including Zero and One. Must eventually be converted to a full TermArg evaluation. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dsfield.c b/drivers/acpi/dispatcher/dsfield.c index a6d77ef..379dd71 100644 --- a/drivers/acpi/dispatcher/dsfield.c +++ b/drivers/acpi/dispatcher/dsfield.c @@ -133,7 +133,8 @@ acpi_ds_create_buffer_field(union acpi_parse_object *op, } } - /* We could put the returned object (Node) on the object stack for later, + /* + * We could put the returned object (Node) on the object stack for later, * but for now, we will put it in the "op" object that the parser uses, * so we can get it again at the end of this scope */ @@ -514,8 +515,33 @@ acpi_ds_create_bank_field(union acpi_parse_object *op, /* Third arg is the bank_value */ + /* TBD: This arg is a term_arg, not a constant, and must be evaluated */ + arg = arg->common.next; - info.bank_value = (u32) arg->common.value.integer; + + /* Currently, only the following constants are supported */ + + switch (arg->common.aml_opcode) { + case AML_ZERO_OP: + info.bank_value = 0; + break; + + case AML_ONE_OP: + info.bank_value = 1; + break; + + case AML_BYTE_OP: + case AML_WORD_OP: + case AML_DWORD_OP: + case AML_QWORD_OP: + info.bank_value = (u32) arg->common.value.integer; + break; + + default: + info.bank_value = 0; + ACPI_ERROR((AE_INFO, + "Non-constant BankValue for BankField is not implemented")); + } /* Fourth arg is the field flags */ -- cgit v0.10.2 From f93a21c7184de3db962d01f11eb2ddad5396c824 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Update version to 20060721 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index ebc1f69..7ece213 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20060707 +#define ACPI_CA_VERSION 0x20060721 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, -- cgit v0.10.2 From 2e42005bcdb4f63bed1cea7f537a5534d4bd7a57 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Update debug output Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evgpe.c b/drivers/acpi/events/evgpe.c index c76c058..1f98818 100644 --- a/drivers/acpi/events/evgpe.c +++ b/drivers/acpi/events/evgpe.c @@ -570,7 +570,7 @@ static void ACPI_SYSTEM_XFACE acpi_ev_asynch_execute_gpe_method(void *context) if (ACPI_FAILURE(status)) { ACPI_EXCEPTION((AE_INFO, status, - "While evaluating GPE method [%4.4s]", + "while evaluating GPE method [%4.4s]", acpi_ut_get_node_name (local_gpe_event_info.dispatch. method_node))); -- cgit v0.10.2 From f3d2e7865c816258c699ff965768e46b50d536d3 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:18 +0300 Subject: ACPICA: Implement simplified Table Manager The Table Manager component has been completely redesigned and reimplemented. The new design is much simpler, and reduces the overall code and data size of the kernel-resident ACPICA by approximately 5%. Also, it is now possible to obtain the ACPI tables very early during kernel initialization, even before dynamic memory management is initialized. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dsinit.c b/drivers/acpi/dispatcher/dsinit.c index 1888c05..9db09de 100644 --- a/drivers/acpi/dispatcher/dsinit.c +++ b/drivers/acpi/dispatcher/dsinit.c @@ -44,6 +44,7 @@ #include #include #include +#include #define _COMPONENT ACPI_DISPATCHER ACPI_MODULE_NAME("dsinit") @@ -90,7 +91,7 @@ acpi_ds_init_one_object(acpi_handle obj_handle, * We are only interested in NS nodes owned by the table that * was just loaded */ - if (node->owner_id != info->table_desc->owner_id) { + if (node->owner_id != info->owner_id) { return (AE_OK); } @@ -150,14 +151,21 @@ acpi_ds_init_one_object(acpi_handle obj_handle, ******************************************************************************/ acpi_status -acpi_ds_initialize_objects(struct acpi_table_desc * table_desc, +acpi_ds_initialize_objects(acpi_native_uint table_index, struct acpi_namespace_node * start_node) { acpi_status status; struct acpi_init_walk_info info; + struct acpi_table_header *table; + acpi_owner_id owner_id; ACPI_FUNCTION_TRACE(ds_initialize_objects); + status = acpi_tb_get_owner_id(table_index, &owner_id); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + ACPI_DEBUG_PRINT((ACPI_DB_DISPATCH, "**** Starting initialization of namespace objects ****\n")); ACPI_DEBUG_PRINT_RAW((ACPI_DB_INIT, "Parsing all Control Methods:")); @@ -166,7 +174,8 @@ acpi_ds_initialize_objects(struct acpi_table_desc * table_desc, info.op_region_count = 0; info.object_count = 0; info.device_count = 0; - info.table_desc = table_desc; + info.table_index = table_index; + info.owner_id = owner_id; /* Walk entire namespace from the supplied root */ @@ -176,10 +185,14 @@ acpi_ds_initialize_objects(struct acpi_table_desc * table_desc, ACPI_EXCEPTION((AE_INFO, status, "During WalkNamespace")); } + status = acpi_get_table_by_index(table_index, &table); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + ACPI_DEBUG_PRINT_RAW((ACPI_DB_INIT, "\nTable [%4.4s](id %4.4X) - %hd Objects with %hd Devices %hd Methods %hd Regions\n", - table_desc->pointer->signature, - table_desc->owner_id, info.object_count, + table->signature, owner_id, info.object_count, info.device_count, info.method_count, info.op_region_count)); diff --git a/drivers/acpi/events/evevent.c b/drivers/acpi/events/evevent.c index 919037d..6b4bc99 100644 --- a/drivers/acpi/events/evevent.c +++ b/drivers/acpi/events/evevent.c @@ -70,13 +70,6 @@ acpi_status acpi_ev_initialize_events(void) ACPI_FUNCTION_TRACE(ev_initialize_events); - /* Make sure we have ACPI tables */ - - if (!acpi_gbl_DSDT) { - ACPI_WARNING((AE_INFO, "No ACPI tables present!")); - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - /* * Initialize the Fixed and General Purpose Events. This is done prior to * enabling SCIs to prevent interrupts from occurring before the handlers are diff --git a/drivers/acpi/events/evgpeblk.c b/drivers/acpi/events/evgpeblk.c index 95ddeb4..bb0eb50 100644 --- a/drivers/acpi/events/evgpeblk.c +++ b/drivers/acpi/events/evgpeblk.c @@ -529,7 +529,7 @@ static struct acpi_gpe_xrupt_info *acpi_ev_get_gpe_xrupt_block(u32 /* Install new interrupt handler if not SCI_INT */ - if (interrupt_number != acpi_gbl_FADT->sci_int) { + if (interrupt_number != acpi_gbl_FADT.sci_interrupt) { status = acpi_os_install_interrupt_handler(interrupt_number, acpi_ev_gpe_xrupt_handler, gpe_xrupt); @@ -567,7 +567,7 @@ acpi_ev_delete_gpe_xrupt(struct acpi_gpe_xrupt_info *gpe_xrupt) /* We never want to remove the SCI interrupt handler */ - if (gpe_xrupt->interrupt_number == acpi_gbl_FADT->sci_int) { + if (gpe_xrupt->interrupt_number == acpi_gbl_FADT.sci_interrupt) { gpe_xrupt->gpe_block_list_head = NULL; return_ACPI_STATUS(AE_OK); } @@ -803,17 +803,17 @@ acpi_ev_create_gpe_info_blocks(struct acpi_gpe_block_info *gpe_block) (gpe_block->block_address.address + i + gpe_block->register_count)); - this_register->status_address.address_space_id = - gpe_block->block_address.address_space_id; - this_register->enable_address.address_space_id = - gpe_block->block_address.address_space_id; - this_register->status_address.register_bit_width = + this_register->status_address.space_id = + gpe_block->block_address.space_id; + this_register->enable_address.space_id = + gpe_block->block_address.space_id; + this_register->status_address.bit_width = ACPI_GPE_REGISTER_WIDTH; - this_register->enable_address.register_bit_width = + this_register->enable_address.bit_width = ACPI_GPE_REGISTER_WIDTH; - this_register->status_address.register_bit_offset = + this_register->status_address.bit_offset = ACPI_GPE_REGISTER_WIDTH; - this_register->enable_address.register_bit_offset = + this_register->enable_address.bit_offset = ACPI_GPE_REGISTER_WIDTH; /* Init the event_info for each GPE within this register */ @@ -1109,11 +1109,12 @@ acpi_status acpi_ev_gpe_initialize(void) * If EITHER the register length OR the block address are zero, then that * particular block is not supported. */ - if (acpi_gbl_FADT->gpe0_blk_len && acpi_gbl_FADT->xgpe0_blk.address) { + if (acpi_gbl_FADT.gpe0_block_length && + acpi_gbl_FADT.xgpe0_block.address) { /* GPE block 0 exists (has both length and address > 0) */ - register_count0 = (u16) (acpi_gbl_FADT->gpe0_blk_len / 2); + register_count0 = (u16) (acpi_gbl_FADT.gpe0_block_length / 2); gpe_number_max = (register_count0 * ACPI_GPE_REGISTER_WIDTH) - 1; @@ -1121,9 +1122,9 @@ acpi_status acpi_ev_gpe_initialize(void) /* Install GPE Block 0 */ status = acpi_ev_create_gpe_block(acpi_gbl_fadt_gpe_device, - &acpi_gbl_FADT->xgpe0_blk, + &acpi_gbl_FADT.xgpe0_block, register_count0, 0, - acpi_gbl_FADT->sci_int, + acpi_gbl_FADT.sci_interrupt, &acpi_gbl_gpe_fadt_blocks[0]); if (ACPI_FAILURE(status)) { @@ -1132,20 +1133,21 @@ acpi_status acpi_ev_gpe_initialize(void) } } - if (acpi_gbl_FADT->gpe1_blk_len && acpi_gbl_FADT->xgpe1_blk.address) { + if (acpi_gbl_FADT.gpe1_block_length && + acpi_gbl_FADT.xgpe1_block.address) { /* GPE block 1 exists (has both length and address > 0) */ - register_count1 = (u16) (acpi_gbl_FADT->gpe1_blk_len / 2); + register_count1 = (u16) (acpi_gbl_FADT.gpe1_block_length / 2); /* Check for GPE0/GPE1 overlap (if both banks exist) */ if ((register_count0) && - (gpe_number_max >= acpi_gbl_FADT->gpe1_base)) { + (gpe_number_max >= acpi_gbl_FADT.gpe1_base)) { ACPI_ERROR((AE_INFO, "GPE0 block (GPE 0 to %d) overlaps the GPE1 block (GPE %d to %d) - Ignoring GPE1", - gpe_number_max, acpi_gbl_FADT->gpe1_base, - acpi_gbl_FADT->gpe1_base + + gpe_number_max, acpi_gbl_FADT.gpe1_base, + acpi_gbl_FADT.gpe1_base + ((register_count1 * ACPI_GPE_REGISTER_WIDTH) - 1))); @@ -1157,10 +1159,11 @@ acpi_status acpi_ev_gpe_initialize(void) status = acpi_ev_create_gpe_block(acpi_gbl_fadt_gpe_device, - &acpi_gbl_FADT->xgpe1_blk, + &acpi_gbl_FADT.xgpe1_block, register_count1, - acpi_gbl_FADT->gpe1_base, - acpi_gbl_FADT->sci_int, + acpi_gbl_FADT.gpe1_base, + acpi_gbl_FADT. + sci_interrupt, &acpi_gbl_gpe_fadt_blocks [1]); @@ -1173,7 +1176,7 @@ acpi_status acpi_ev_gpe_initialize(void) * GPE0 and GPE1 do not have to be contiguous in the GPE number * space. However, GPE0 always starts at GPE number zero. */ - gpe_number_max = acpi_gbl_FADT->gpe1_base + + gpe_number_max = acpi_gbl_FADT.gpe1_base + ((register_count1 * ACPI_GPE_REGISTER_WIDTH) - 1); } } diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index 00f33ed..21449f3 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c @@ -63,6 +63,10 @@ static const char *acpi_notify_value_names[] = { }; #endif +/* Pointer to FACS needed for the Global Lock */ + +static struct acpi_table_facs *facs = NULL; + /* Local prototypes */ static void ACPI_SYSTEM_XFACE acpi_ev_notify_dispatch(void *context); @@ -306,7 +310,7 @@ static u32 acpi_ev_global_lock_handler(void *context) * If we don't get it now, it will be marked pending and we will * take another interrupt when it becomes free. */ - ACPI_ACQUIRE_GLOBAL_LOCK(acpi_gbl_common_fACS.global_lock, acquired); + ACPI_ACQUIRE_GLOBAL_LOCK(facs, acquired); if (acquired) { /* Got the lock, now wake all threads waiting for it */ @@ -342,6 +346,13 @@ acpi_status acpi_ev_init_global_lock_handler(void) ACPI_FUNCTION_TRACE(ev_init_global_lock_handler); + status = + acpi_get_table(ACPI_SIG_FACS, 0, + (struct acpi_table_header **)&facs); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + acpi_gbl_global_lock_present = TRUE; status = acpi_install_fixed_event_handler(ACPI_EVENT_GLOBAL, acpi_ev_global_lock_handler, @@ -414,7 +425,7 @@ acpi_status acpi_ev_acquire_global_lock(u16 timeout) /* Attempt to acquire the actual hardware lock */ - ACPI_ACQUIRE_GLOBAL_LOCK(acpi_gbl_common_fACS.global_lock, acquired); + ACPI_ACQUIRE_GLOBAL_LOCK(facs, acquired); if (acquired) { /* We got the lock */ @@ -438,6 +449,7 @@ acpi_status acpi_ev_acquire_global_lock(u16 timeout) */ status = acpi_ex_system_wait_semaphore(acpi_gbl_global_lock_semaphore, ACPI_WAIT_FOREVER); + return_ACPI_STATUS(status); } @@ -472,8 +484,7 @@ acpi_status acpi_ev_release_global_lock(void) /* Allow any thread to release the lock */ - ACPI_RELEASE_GLOBAL_LOCK(acpi_gbl_common_fACS.global_lock, - pending); + ACPI_RELEASE_GLOBAL_LOCK(facs, pending); /* * If the pending bit was set, we must write GBL_RLS to the control diff --git a/drivers/acpi/events/evsci.c b/drivers/acpi/events/evsci.c index 8106215..d7680ac 100644 --- a/drivers/acpi/events/evsci.c +++ b/drivers/acpi/events/evsci.c @@ -142,9 +142,10 @@ u32 acpi_ev_install_sci_handler(void) ACPI_FUNCTION_TRACE(ev_install_sci_handler); - status = acpi_os_install_interrupt_handler((u32) acpi_gbl_FADT->sci_int, - acpi_ev_sci_xrupt_handler, - acpi_gbl_gpe_xrupt_list_head); + status = + acpi_os_install_interrupt_handler((u32) acpi_gbl_FADT.sci_interrupt, + acpi_ev_sci_xrupt_handler, + acpi_gbl_gpe_xrupt_list_head); return_ACPI_STATUS(status); } @@ -175,8 +176,9 @@ acpi_status acpi_ev_remove_sci_handler(void) /* Just let the OS remove the handler and disable the level */ - status = acpi_os_remove_interrupt_handler((u32) acpi_gbl_FADT->sci_int, - acpi_ev_sci_xrupt_handler); + status = + acpi_os_remove_interrupt_handler((u32) acpi_gbl_FADT.sci_interrupt, + acpi_ev_sci_xrupt_handler); return_ACPI_STATUS(status); } diff --git a/drivers/acpi/events/evxfevnt.c b/drivers/acpi/events/evxfevnt.c index 7ebc2ef..91e5f5b 100644 --- a/drivers/acpi/events/evxfevnt.c +++ b/drivers/acpi/events/evxfevnt.c @@ -65,13 +65,6 @@ acpi_status acpi_enable(void) ACPI_FUNCTION_TRACE(acpi_enable); - /* Make sure we have the FADT */ - - if (!acpi_gbl_FADT) { - ACPI_WARNING((AE_INFO, "No FADT information present!")); - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - if (acpi_hw_get_mode() == ACPI_SYS_MODE_ACPI) { ACPI_DEBUG_PRINT((ACPI_DB_INIT, "System is already in ACPI mode\n")); @@ -111,11 +104,6 @@ acpi_status acpi_disable(void) ACPI_FUNCTION_TRACE(acpi_disable); - if (!acpi_gbl_FADT) { - ACPI_WARNING((AE_INFO, "No FADT information present!")); - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - if (acpi_hw_get_mode() == ACPI_SYS_MODE_LEGACY) { ACPI_DEBUG_PRINT((ACPI_DB_INIT, "System is already in legacy (non-ACPI) mode\n")); diff --git a/drivers/acpi/executer/exconfig.c b/drivers/acpi/executer/exconfig.c index c8341fa..dd43b00 100644 --- a/drivers/acpi/executer/exconfig.c +++ b/drivers/acpi/executer/exconfig.c @@ -54,7 +54,7 @@ ACPI_MODULE_NAME("exconfig") /* Local prototypes */ static acpi_status -acpi_ex_add_table(struct acpi_table_header *table, +acpi_ex_add_table(acpi_native_uint table_index, struct acpi_namespace_node *parent_node, union acpi_operand_object **ddb_handle); @@ -74,12 +74,11 @@ acpi_ex_add_table(struct acpi_table_header *table, ******************************************************************************/ static acpi_status -acpi_ex_add_table(struct acpi_table_header *table, +acpi_ex_add_table(acpi_native_uint table_index, struct acpi_namespace_node *parent_node, union acpi_operand_object **ddb_handle) { acpi_status status; - struct acpi_table_desc table_info; union acpi_operand_object *obj_desc; ACPI_FUNCTION_TRACE(ex_add_table); @@ -98,42 +97,16 @@ acpi_ex_add_table(struct acpi_table_header *table, /* Install the new table into the local data structures */ - ACPI_MEMSET(&table_info, 0, sizeof(struct acpi_table_desc)); - - table_info.type = ACPI_TABLE_ID_SSDT; - table_info.pointer = table; - table_info.length = (acpi_size) table->length; - table_info.allocation = ACPI_MEM_ALLOCATED; - - status = acpi_tb_install_table(&table_info); - obj_desc->reference.object = table_info.installed_desc; - - if (ACPI_FAILURE(status)) { - if (status == AE_ALREADY_EXISTS) { - - /* Table already exists, just return the handle */ - - return_ACPI_STATUS(AE_OK); - } - goto cleanup; - } + obj_desc->reference.object = ACPI_CAST_PTR(void, table_index); /* Add the table to the namespace */ - status = acpi_ns_load_table(table_info.installed_desc, parent_node); + status = acpi_ns_load_table(table_index, parent_node); if (ACPI_FAILURE(status)) { - - /* Uninstall table on error */ - - (void)acpi_tb_uninstall_table(table_info.installed_desc); - goto cleanup; + acpi_ut_remove_reference(obj_desc); + *ddb_handle = NULL; } - return_ACPI_STATUS(AE_OK); - - cleanup: - acpi_ut_remove_reference(obj_desc); - *ddb_handle = NULL; return_ACPI_STATUS(status); } @@ -156,11 +129,12 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state, { acpi_status status; union acpi_operand_object **operand = &walk_state->operands[0]; - struct acpi_table_header *table; + acpi_native_uint table_index; struct acpi_namespace_node *parent_node; struct acpi_namespace_node *start_node; struct acpi_namespace_node *parameter_node = NULL; union acpi_operand_object *ddb_handle; + struct acpi_table_header *table; ACPI_FUNCTION_TRACE(ex_load_table_op); @@ -182,7 +156,7 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state, status = acpi_tb_find_table(operand[0]->string.pointer, operand[1]->string.pointer, - operand[2]->string.pointer, &table); + operand[2]->string.pointer, &table_index); if (ACPI_FAILURE(status)) { if (status != AE_NOT_FOUND) { return_ACPI_STATUS(status); @@ -245,7 +219,7 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state, /* Load the table into the namespace */ - status = acpi_ex_add_table(table, parent_node, &ddb_handle); + status = acpi_ex_add_table(table_index, parent_node, &ddb_handle); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -266,9 +240,13 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state, } } - ACPI_INFO((AE_INFO, - "Dynamic OEM Table Load - [%4.4s] OemId [%6.6s] OemTableId [%8.8s]", - table->signature, table->oem_id, table->oem_table_id)); + status = acpi_get_table_by_index(table_index, &table); + if (ACPI_SUCCESS(status)) { + ACPI_INFO((AE_INFO, + "Dynamic OEM Table Load - [%4.4s] OemId [%6.6s] OemTableId [%8.8s]", + table->signature, table->oem_id, + table->oem_table_id)); + } *return_desc = ddb_handle; return_ACPI_STATUS(status); @@ -298,6 +276,7 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, union acpi_operand_object *ddb_handle; union acpi_operand_object *buffer_desc = NULL; struct acpi_table_header *table_ptr = NULL; + acpi_native_uint table_index; acpi_physical_address address; struct acpi_table_header table_header; acpi_integer temp; @@ -420,8 +399,8 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, /* The table must be either an SSDT or a PSDT */ - if ((!ACPI_COMPARE_NAME(table_ptr->signature, PSDT_SIG)) && - (!ACPI_COMPARE_NAME(table_ptr->signature, SSDT_SIG))) { + if ((!ACPI_COMPARE_NAME(table_ptr->signature, ACPI_SIG_PSDT)) && + (!ACPI_COMPARE_NAME(table_ptr->signature, ACPI_SIG_SSDT))) { ACPI_ERROR((AE_INFO, "Table has invalid signature [%4.4s], must be SSDT or PSDT", table_ptr->signature)); @@ -429,9 +408,16 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, goto cleanup; } - /* Install the new table into the local data structures */ + /* + * Install the new table into the local data structures + */ + status = acpi_tb_add_table(table_ptr, &table_index); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } - status = acpi_ex_add_table(table_ptr, acpi_gbl_root_node, &ddb_handle); + status = + acpi_ex_add_table(table_index, acpi_gbl_root_node, &ddb_handle); if (ACPI_FAILURE(status)) { /* On error, table_ptr was deallocated above */ @@ -477,7 +463,7 @@ acpi_status acpi_ex_unload_table(union acpi_operand_object *ddb_handle) { acpi_status status = AE_OK; union acpi_operand_object *table_desc = ddb_handle; - struct acpi_table_desc *table_info; + acpi_native_uint table_index; ACPI_FUNCTION_TRACE(ex_unload_table); @@ -493,19 +479,18 @@ acpi_status acpi_ex_unload_table(union acpi_operand_object *ddb_handle) return_ACPI_STATUS(AE_BAD_PARAMETER); } - /* Get the actual table descriptor from the ddb_handle */ + /* Get the table index from the ddb_handle */ - table_info = (struct acpi_table_desc *)table_desc->reference.object; + table_index = (acpi_native_uint) table_desc->reference.object; /* * Delete the entire namespace under this table Node * (Offset contains the table_id) */ - acpi_ns_delete_namespace_by_owner(table_info->owner_id); - - /* Delete the table itself */ + acpi_tb_delete_namespace_by_owner(table_index); + acpi_tb_release_owner_id(table_index); - (void)acpi_tb_uninstall_table(table_info->installed_desc); + acpi_tb_set_table_loaded_flag(table_index, FALSE); /* Delete the table descriptor (ddb_handle) */ diff --git a/drivers/acpi/executer/excreate.c b/drivers/acpi/executer/excreate.c index 34eec82..a4d29b2 100644 --- a/drivers/acpi/executer/excreate.c +++ b/drivers/acpi/executer/excreate.c @@ -359,8 +359,9 @@ acpi_status acpi_ex_create_table_region(struct acpi_walk_state *walk_state) union acpi_operand_object **operand = &walk_state->operands[0]; union acpi_operand_object *obj_desc; struct acpi_namespace_node *node; - struct acpi_table_header *table; union acpi_operand_object *region_obj2; + acpi_native_uint table_index; + struct acpi_table_header *table; ACPI_FUNCTION_TRACE(ex_create_table_region); @@ -380,7 +381,7 @@ acpi_status acpi_ex_create_table_region(struct acpi_walk_state *walk_state) status = acpi_tb_find_table(operand[1]->string.pointer, operand[2]->string.pointer, - operand[3]->string.pointer, &table); + operand[3]->string.pointer, &table_index); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -395,6 +396,11 @@ acpi_status acpi_ex_create_table_region(struct acpi_walk_state *walk_state) region_obj2 = obj_desc->common.next_object; region_obj2->extra.region_context = NULL; + status = acpi_get_table_by_index(table_index, &table); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + /* Init the region from the operands */ obj_desc->region.space_id = REGION_DATA_TABLE; @@ -553,7 +559,8 @@ acpi_ex_create_method(u8 * aml_start, obj_desc = acpi_ut_create_internal_object(ACPI_TYPE_METHOD); if (!obj_desc) { - return_ACPI_STATUS(AE_NO_MEMORY); + status = AE_NO_MEMORY; + goto exit; } /* Save the method's AML pointer and length */ @@ -597,6 +604,7 @@ acpi_ex_create_method(u8 * aml_start, acpi_ut_remove_reference(obj_desc); + exit: /* Remove a reference to the operand */ acpi_ut_remove_reference(operand[1]); diff --git a/drivers/acpi/executer/exfldio.c b/drivers/acpi/executer/exfldio.c index 40f0bee..b3f30d8 100644 --- a/drivers/acpi/executer/exfldio.c +++ b/drivers/acpi/executer/exfldio.c @@ -257,14 +257,13 @@ acpi_ex_access_region(union acpi_operand_object *obj_desc, } ACPI_DEBUG_PRINT_RAW((ACPI_DB_BFIELD, - " Region [%s:%X], Width %X, ByteBase %X, Offset %X at %8.8X%8.8X\n", + " Region [%s:%X], Width %X, ByteBase %X, Offset %X at %p\n", acpi_ut_get_region_name(rgn_desc->region. space_id), rgn_desc->region.space_id, obj_desc->common_field.access_byte_width, obj_desc->common_field.base_byte_offset, - field_datum_byte_offset, - ACPI_FORMAT_UINT64(address))); + field_datum_byte_offset, (void *)address)); /* Invoke the appropriate address_space/op_region handler */ diff --git a/drivers/acpi/executer/exregion.c b/drivers/acpi/executer/exregion.c index 3cc97ba..4967447 100644 --- a/drivers/acpi/executer/exregion.c +++ b/drivers/acpi/executer/exregion.c @@ -155,16 +155,15 @@ acpi_ex_system_memory_space_handler(u32 function, /* Create a new mapping starting at the address given */ - status = acpi_os_map_memory(address, window_size, - (void **)&mem_info-> - mapped_logical_address); - if (ACPI_FAILURE(status)) { + mem_info->mapped_logical_address = + acpi_os_map_memory((acpi_native_uint) address, window_size); + if (!mem_info->mapped_logical_address) { ACPI_ERROR((AE_INFO, "Could not map memory at %8.8X%8.8X, size %X", ACPI_FORMAT_UINT64(address), (u32) window_size)); mem_info->mapped_length = 0; - return_ACPI_STATUS(status); + return_ACPI_STATUS(AE_NO_MEMORY); } /* Save the physical address and mapping size */ diff --git a/drivers/acpi/hardware/hwacpi.c b/drivers/acpi/hardware/hwacpi.c index de50fab..14e8111 100644 --- a/drivers/acpi/hardware/hwacpi.c +++ b/drivers/acpi/hardware/hwacpi.c @@ -65,13 +65,6 @@ acpi_status acpi_hw_initialize(void) ACPI_FUNCTION_TRACE(hw_initialize); - /* We must have the ACPI tables by the time we get here */ - - if (!acpi_gbl_FADT) { - ACPI_ERROR((AE_INFO, "No FADT is present")); - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - /* Sanity check the FADT for valid values */ status = acpi_ut_validate_fadt(); @@ -106,7 +99,7 @@ acpi_status acpi_hw_set_mode(u32 mode) * ACPI 2.0 clarified that if SMI_CMD in FADT is zero, * system does not support mode transition. */ - if (!acpi_gbl_FADT->smi_cmd) { + if (!acpi_gbl_FADT.smi_command) { ACPI_ERROR((AE_INFO, "No SMI_CMD in FADT, mode transition failed")); return_ACPI_STATUS(AE_NO_HARDWARE_RESPONSE); @@ -119,7 +112,7 @@ acpi_status acpi_hw_set_mode(u32 mode) * we make sure both the numbers are zero to determine these * transitions are not supported. */ - if (!acpi_gbl_FADT->acpi_enable && !acpi_gbl_FADT->acpi_disable) { + if (!acpi_gbl_FADT.acpi_enable && !acpi_gbl_FADT.acpi_disable) { ACPI_ERROR((AE_INFO, "No ACPI mode transition supported in this system (enable/disable both zero)")); return_ACPI_STATUS(AE_OK); @@ -130,9 +123,8 @@ acpi_status acpi_hw_set_mode(u32 mode) /* BIOS should have disabled ALL fixed and GP events */ - status = acpi_os_write_port(acpi_gbl_FADT->smi_cmd, - (u32) acpi_gbl_FADT->acpi_enable, - 8); + status = acpi_os_write_port(acpi_gbl_FADT.smi_command, + (u32) acpi_gbl_FADT.acpi_enable, 8); ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Attempting to enable ACPI mode\n")); break; @@ -143,8 +135,8 @@ acpi_status acpi_hw_set_mode(u32 mode) * BIOS should clear all fixed status bits and restore fixed event * enable bits to default */ - status = acpi_os_write_port(acpi_gbl_FADT->smi_cmd, - (u32) acpi_gbl_FADT->acpi_disable, + status = acpi_os_write_port(acpi_gbl_FADT.smi_command, + (u32) acpi_gbl_FADT.acpi_disable, 8); ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Attempting to enable Legacy (non-ACPI) mode\n")); @@ -204,7 +196,7 @@ u32 acpi_hw_get_mode(void) * ACPI 2.0 clarified that if SMI_CMD in FADT is zero, * system does not support mode transition. */ - if (!acpi_gbl_FADT->smi_cmd) { + if (!acpi_gbl_FADT.smi_command) { return_UINT32(ACPI_SYS_MODE_ACPI); } diff --git a/drivers/acpi/hardware/hwregs.c b/drivers/acpi/hardware/hwregs.c index fa58c1e..9fe7adf 100644 --- a/drivers/acpi/hardware/hwregs.c +++ b/drivers/acpi/hardware/hwregs.c @@ -73,7 +73,7 @@ acpi_status acpi_hw_clear_acpi_status(u32 flags) ACPI_DEBUG_PRINT((ACPI_DB_IO, "About to write %04X to %04X\n", ACPI_BITMASK_ALL_FIXED_STATUS, - (u16) acpi_gbl_FADT->xpm1a_evt_blk.address)); + (u16) acpi_gbl_FADT.xpm1a_event_block.address)); lock_flags = acpi_os_acquire_lock(acpi_gbl_hardware_lock); @@ -86,10 +86,10 @@ acpi_status acpi_hw_clear_acpi_status(u32 flags) /* Clear the fixed events */ - if (acpi_gbl_FADT->xpm1b_evt_blk.address) { + if (acpi_gbl_FADT.xpm1b_event_block.address) { status = acpi_hw_low_level_write(16, ACPI_BITMASK_ALL_FIXED_STATUS, - &acpi_gbl_FADT->xpm1b_evt_blk); + &acpi_gbl_FADT.xpm1b_event_block); if (ACPI_FAILURE(status)) { goto unlock_and_exit; } @@ -422,8 +422,9 @@ acpi_status acpi_set_register(u32 register_id, u32 value, u32 flags) ACPI_DEBUG_PRINT((ACPI_DB_IO, "PM2 control: Read %X from %8.8X%8.8X\n", register_value, - ACPI_FORMAT_UINT64(acpi_gbl_FADT-> - xpm2_cnt_blk.address))); + ACPI_FORMAT_UINT64(acpi_gbl_FADT. + xpm2_control_block. + address))); ACPI_REGISTER_INSERT_VALUE(register_value, bit_reg_info->bit_position, @@ -433,8 +434,9 @@ acpi_status acpi_set_register(u32 register_id, u32 value, u32 flags) ACPI_DEBUG_PRINT((ACPI_DB_IO, "About to write %4.4X to %8.8X%8.8X\n", register_value, - ACPI_FORMAT_UINT64(acpi_gbl_FADT-> - xpm2_cnt_blk.address))); + ACPI_FORMAT_UINT64(acpi_gbl_FADT. + xpm2_control_block. + address))); status = acpi_hw_register_write(ACPI_MTX_DO_NOT_LOCK, ACPI_REGISTER_PM2_CONTROL, @@ -495,7 +497,7 @@ acpi_hw_register_read(u8 use_lock, u32 register_id, u32 * return_value) status = acpi_hw_low_level_read(16, &value1, - &acpi_gbl_FADT->xpm1a_evt_blk); + &acpi_gbl_FADT.xpm1a_event_block); if (ACPI_FAILURE(status)) { goto unlock_and_exit; } @@ -504,7 +506,7 @@ acpi_hw_register_read(u8 use_lock, u32 register_id, u32 * return_value) status = acpi_hw_low_level_read(16, &value2, - &acpi_gbl_FADT->xpm1b_evt_blk); + &acpi_gbl_FADT.xpm1b_event_block); value1 |= value2; break; @@ -527,14 +529,14 @@ acpi_hw_register_read(u8 use_lock, u32 register_id, u32 * return_value) status = acpi_hw_low_level_read(16, &value1, - &acpi_gbl_FADT->xpm1a_cnt_blk); + &acpi_gbl_FADT.xpm1a_control_block); if (ACPI_FAILURE(status)) { goto unlock_and_exit; } status = acpi_hw_low_level_read(16, &value2, - &acpi_gbl_FADT->xpm1b_cnt_blk); + &acpi_gbl_FADT.xpm1b_control_block); value1 |= value2; break; @@ -542,19 +544,20 @@ acpi_hw_register_read(u8 use_lock, u32 register_id, u32 * return_value) status = acpi_hw_low_level_read(8, &value1, - &acpi_gbl_FADT->xpm2_cnt_blk); + &acpi_gbl_FADT.xpm2_control_block); break; case ACPI_REGISTER_PM_TIMER: /* 32-bit access */ status = acpi_hw_low_level_read(32, &value1, - &acpi_gbl_FADT->xpm_tmr_blk); + &acpi_gbl_FADT.xpm_timer_block); break; case ACPI_REGISTER_SMI_COMMAND_BLOCK: /* 8-bit access */ - status = acpi_os_read_port(acpi_gbl_FADT->smi_cmd, &value1, 8); + status = + acpi_os_read_port(acpi_gbl_FADT.smi_command, &value1, 8); break; default: @@ -635,7 +638,7 @@ acpi_status acpi_hw_register_write(u8 use_lock, u32 register_id, u32 value) status = acpi_hw_low_level_write(16, value, - &acpi_gbl_FADT->xpm1a_evt_blk); + &acpi_gbl_FADT.xpm1a_event_block); if (ACPI_FAILURE(status)) { goto unlock_and_exit; } @@ -644,7 +647,7 @@ acpi_status acpi_hw_register_write(u8 use_lock, u32 register_id, u32 value) status = acpi_hw_low_level_write(16, value, - &acpi_gbl_FADT->xpm1b_evt_blk); + &acpi_gbl_FADT.xpm1b_event_block); break; case ACPI_REGISTER_PM1_ENABLE: /* 16-bit access */ @@ -682,49 +685,50 @@ acpi_status acpi_hw_register_write(u8 use_lock, u32 register_id, u32 value) status = acpi_hw_low_level_write(16, value, - &acpi_gbl_FADT->xpm1a_cnt_blk); + &acpi_gbl_FADT.xpm1a_control_block); if (ACPI_FAILURE(status)) { goto unlock_and_exit; } status = acpi_hw_low_level_write(16, value, - &acpi_gbl_FADT->xpm1b_cnt_blk); + &acpi_gbl_FADT.xpm1b_control_block); break; case ACPI_REGISTER_PM1A_CONTROL: /* 16-bit access */ status = acpi_hw_low_level_write(16, value, - &acpi_gbl_FADT->xpm1a_cnt_blk); + &acpi_gbl_FADT.xpm1a_control_block); break; case ACPI_REGISTER_PM1B_CONTROL: /* 16-bit access */ status = acpi_hw_low_level_write(16, value, - &acpi_gbl_FADT->xpm1b_cnt_blk); + &acpi_gbl_FADT.xpm1b_control_block); break; case ACPI_REGISTER_PM2_CONTROL: /* 8-bit access */ status = acpi_hw_low_level_write(8, value, - &acpi_gbl_FADT->xpm2_cnt_blk); + &acpi_gbl_FADT.xpm2_control_block); break; case ACPI_REGISTER_PM_TIMER: /* 32-bit access */ status = acpi_hw_low_level_write(32, value, - &acpi_gbl_FADT->xpm_tmr_blk); + &acpi_gbl_FADT.xpm_timer_block); break; case ACPI_REGISTER_SMI_COMMAND_BLOCK: /* 8-bit access */ /* SMI_CMD is currently always in IO space */ - status = acpi_os_write_port(acpi_gbl_FADT->smi_cmd, value, 8); + status = + acpi_os_write_port(acpi_gbl_FADT.smi_command, value, 8); break; default: @@ -783,7 +787,7 @@ acpi_hw_low_level_read(u32 width, u32 * value, struct acpi_generic_address *reg) * Two address spaces supported: Memory or IO. * PCI_Config is not supported here because the GAS struct is insufficient */ - switch (reg->address_space_id) { + switch (reg->space_id) { case ACPI_ADR_SPACE_SYSTEM_MEMORY: status = acpi_os_read_memory((acpi_physical_address) address, @@ -798,8 +802,7 @@ acpi_hw_low_level_read(u32 width, u32 * value, struct acpi_generic_address *reg) default: ACPI_ERROR((AE_INFO, - "Unsupported address space: %X", - reg->address_space_id)); + "Unsupported address space: %X", reg->space_id)); return (AE_BAD_PARAMETER); } @@ -807,7 +810,7 @@ acpi_hw_low_level_read(u32 width, u32 * value, struct acpi_generic_address *reg) "Read: %8.8X width %2d from %8.8X%8.8X (%s)\n", *value, width, ACPI_FORMAT_UINT64(address), - acpi_ut_get_region_name(reg->address_space_id))); + acpi_ut_get_region_name(reg->space_id))); return (status); } @@ -854,7 +857,7 @@ acpi_hw_low_level_write(u32 width, u32 value, struct acpi_generic_address * reg) * Two address spaces supported: Memory or IO. * PCI_Config is not supported here because the GAS struct is insufficient */ - switch (reg->address_space_id) { + switch (reg->space_id) { case ACPI_ADR_SPACE_SYSTEM_MEMORY: status = acpi_os_write_memory((acpi_physical_address) address, @@ -869,8 +872,7 @@ acpi_hw_low_level_write(u32 width, u32 value, struct acpi_generic_address * reg) default: ACPI_ERROR((AE_INFO, - "Unsupported address space: %X", - reg->address_space_id)); + "Unsupported address space: %X", reg->space_id)); return (AE_BAD_PARAMETER); } @@ -878,7 +880,7 @@ acpi_hw_low_level_write(u32 width, u32 value, struct acpi_generic_address * reg) "Wrote: %8.8X width %2d to %8.8X%8.8X (%s)\n", value, width, ACPI_FORMAT_UINT64(address), - acpi_ut_get_region_name(reg->address_space_id))); + acpi_ut_get_region_name(reg->space_id))); return (status); } diff --git a/drivers/acpi/hardware/hwsleep.c b/drivers/acpi/hardware/hwsleep.c index 8bb43ca..6faa76b 100644 --- a/drivers/acpi/hardware/hwsleep.c +++ b/drivers/acpi/hardware/hwsleep.c @@ -43,6 +43,7 @@ */ #include +#include #define _COMPONENT ACPI_HARDWARE ACPI_MODULE_NAME("hwsleep") @@ -62,17 +63,32 @@ ACPI_MODULE_NAME("hwsleep") acpi_status acpi_set_firmware_waking_vector(acpi_physical_address physical_address) { + struct acpi_table_facs *facs; + acpi_status status; ACPI_FUNCTION_TRACE(acpi_set_firmware_waking_vector); + /* Get the FACS */ + + status = + acpi_get_table_by_index(ACPI_TABLE_INDEX_FACS, + (struct acpi_table_header **)&facs); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + /* Set the vector */ - if (acpi_gbl_common_fACS.vector_width == 32) { - *(ACPI_CAST_PTR - (u32, acpi_gbl_common_fACS.firmware_waking_vector)) - = (u32) physical_address; + if ((facs->length < 32) || (!(facs->xfirmware_waking_vector))) { + /* + * ACPI 1.0 FACS or short table or optional X_ field is zero + */ + facs->firmware_waking_vector = (u32) physical_address; } else { - *acpi_gbl_common_fACS.firmware_waking_vector = physical_address; + /* + * ACPI 2.0 FACS with valid X_ field + */ + facs->xfirmware_waking_vector = physical_address; } return_ACPI_STATUS(AE_OK); @@ -97,6 +113,8 @@ ACPI_EXPORT_SYMBOL(acpi_set_firmware_waking_vector) acpi_status acpi_get_firmware_waking_vector(acpi_physical_address * physical_address) { + struct acpi_table_facs *facs; + acpi_status status; ACPI_FUNCTION_TRACE(acpi_get_firmware_waking_vector); @@ -104,16 +122,29 @@ acpi_get_firmware_waking_vector(acpi_physical_address * physical_address) return_ACPI_STATUS(AE_BAD_PARAMETER); } + /* Get the FACS */ + + status = + acpi_get_table_by_index(ACPI_TABLE_INDEX_FACS, + (struct acpi_table_header **)&facs); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + /* Get the vector */ - if (acpi_gbl_common_fACS.vector_width == 32) { - *physical_address = (acpi_physical_address) - * - (ACPI_CAST_PTR - (u32, acpi_gbl_common_fACS.firmware_waking_vector)); + if ((facs->length < 32) || (!(facs->xfirmware_waking_vector))) { + /* + * ACPI 1.0 FACS or short table or optional X_ field is zero + */ + *physical_address = + (acpi_physical_address) facs->firmware_waking_vector; } else { + /* + * ACPI 2.0 FACS with valid X_ field + */ *physical_address = - *acpi_gbl_common_fACS.firmware_waking_vector; + (acpi_physical_address) facs->xfirmware_waking_vector; } return_ACPI_STATUS(AE_OK); @@ -429,8 +460,8 @@ acpi_status asmlinkage acpi_enter_sleep_state_s4bios(void) ACPI_FLUSH_CPU_CACHE(); - status = acpi_os_write_port(acpi_gbl_FADT->smi_cmd, - (u32) acpi_gbl_FADT->S4bios_req, 8); + status = acpi_os_write_port(acpi_gbl_FADT.smi_command, + (u32) acpi_gbl_FADT.S4bios_request, 8); do { acpi_os_stall(1000); diff --git a/drivers/acpi/hardware/hwtimer.c b/drivers/acpi/hardware/hwtimer.c index c4ec47c..abd86e8d 100644 --- a/drivers/acpi/hardware/hwtimer.c +++ b/drivers/acpi/hardware/hwtimer.c @@ -66,7 +66,7 @@ acpi_status acpi_get_timer_resolution(u32 * resolution) return_ACPI_STATUS(AE_BAD_PARAMETER); } - if (acpi_gbl_FADT->tmr_val_ext == 0) { + if ((acpi_gbl_FADT.flags & ACPI_FADT_32BIT_TIMER) == 0) { *resolution = 24; } else { *resolution = 32; @@ -98,7 +98,8 @@ acpi_status acpi_get_timer(u32 * ticks) return_ACPI_STATUS(AE_BAD_PARAMETER); } - status = acpi_hw_low_level_read(32, ticks, &acpi_gbl_FADT->xpm_tmr_blk); + status = + acpi_hw_low_level_read(32, ticks, &acpi_gbl_FADT.xpm_timer_block); return_ACPI_STATUS(status); } @@ -153,7 +154,7 @@ acpi_get_timer_duration(u32 start_ticks, u32 end_ticks, u32 * time_elapsed) if (start_ticks < end_ticks) { delta_ticks = end_ticks - start_ticks; } else if (start_ticks > end_ticks) { - if (acpi_gbl_FADT->tmr_val_ext == 0) { + if ((acpi_gbl_FADT.flags & ACPI_FADT_32BIT_TIMER) == 0) { /* 24-bit Timer */ diff --git a/drivers/acpi/namespace/nsload.c b/drivers/acpi/namespace/nsload.c index fe75d88..5d555f8 100644 --- a/drivers/acpi/namespace/nsload.c +++ b/drivers/acpi/namespace/nsload.c @@ -44,13 +44,12 @@ #include #include #include +#include #define _COMPONENT ACPI_NAMESPACE ACPI_MODULE_NAME("nsload") /* Local prototypes */ -static acpi_status acpi_ns_load_table_by_type(acpi_table_type table_type); - #ifdef ACPI_FUTURE_IMPLEMENTATION acpi_status acpi_ns_unload_namespace(acpi_handle handle); @@ -62,7 +61,7 @@ static acpi_status acpi_ns_delete_subtree(acpi_handle start_handle); * * FUNCTION: acpi_ns_load_table * - * PARAMETERS: table_desc - Descriptor for table to be loaded + * PARAMETERS: table_index - Index for table to be loaded * Node - Owning NS node * * RETURN: Status @@ -72,42 +71,13 @@ static acpi_status acpi_ns_delete_subtree(acpi_handle start_handle); ******************************************************************************/ acpi_status -acpi_ns_load_table(struct acpi_table_desc *table_desc, +acpi_ns_load_table(acpi_native_uint table_index, struct acpi_namespace_node *node) { acpi_status status; ACPI_FUNCTION_TRACE(ns_load_table); - /* Check if table contains valid AML (must be DSDT, PSDT, SSDT, etc.) */ - - if (! - (acpi_gbl_table_data[table_desc->type]. - flags & ACPI_TABLE_EXECUTABLE)) { - - /* Just ignore this table */ - - return_ACPI_STATUS(AE_OK); - } - - /* Check validity of the AML start and length */ - - if (!table_desc->aml_start) { - ACPI_ERROR((AE_INFO, "Null AML pointer")); - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "AML block at %p\n", - table_desc->aml_start)); - - /* Ignore table if there is no AML contained within */ - - if (!table_desc->aml_length) { - ACPI_WARNING((AE_INFO, "Zero-length AML block in table [%4.4s]", - table_desc->pointer->signature)); - return_ACPI_STATUS(AE_OK); - } - /* * Parse the table and load the namespace with all named * objects found within. Control methods are NOT parsed @@ -117,15 +87,34 @@ acpi_ns_load_table(struct acpi_table_desc *table_desc, * to another control method, we can't continue parsing * because we don't know how many arguments to parse next! */ + status = acpi_ut_acquire_mutex(ACPI_MTX_NAMESPACE); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + + /* If table already loaded into namespace, just return */ + + if (acpi_tb_is_table_loaded(table_index)) { + status = AE_ALREADY_EXISTS; + goto unlock; + } + ACPI_DEBUG_PRINT((ACPI_DB_INFO, "**** Loading table into namespace ****\n")); - status = acpi_ut_acquire_mutex(ACPI_MTX_NAMESPACE); + status = acpi_tb_allocate_owner_id(table_index); if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + goto unlock; + } + + status = acpi_ns_parse_table(table_index, node->child); + if (ACPI_SUCCESS(status)) { + acpi_tb_set_table_loaded_flag(table_index, TRUE); + } else { + acpi_tb_release_owner_id(table_index); } - status = acpi_ns_parse_table(table_desc, node->child); + unlock: (void)acpi_ut_release_mutex(ACPI_MTX_NAMESPACE); if (ACPI_FAILURE(status)) { @@ -141,7 +130,7 @@ acpi_ns_load_table(struct acpi_table_desc *table_desc, ACPI_DEBUG_PRINT((ACPI_DB_INFO, "**** Begin Table Method Parsing and Object Initialization ****\n")); - status = acpi_ds_initialize_objects(table_desc, node); + status = acpi_ds_initialize_objects(table_index, node); ACPI_DEBUG_PRINT((ACPI_DB_INFO, "**** Completed Table Method Parsing and Object Initialization ****\n")); @@ -149,99 +138,7 @@ acpi_ns_load_table(struct acpi_table_desc *table_desc, return_ACPI_STATUS(status); } -/******************************************************************************* - * - * FUNCTION: acpi_ns_load_table_by_type - * - * PARAMETERS: table_type - Id of the table type to load - * - * RETURN: Status - * - * DESCRIPTION: Load an ACPI table or tables into the namespace. All tables - * of the given type are loaded. The mechanism allows this - * routine to be called repeatedly. - * - ******************************************************************************/ - -static acpi_status acpi_ns_load_table_by_type(acpi_table_type table_type) -{ - u32 i; - acpi_status status; - struct acpi_table_desc *table_desc; - - ACPI_FUNCTION_TRACE(ns_load_table_by_type); - - status = acpi_ut_acquire_mutex(ACPI_MTX_TABLES); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* - * Table types supported are: - * DSDT (one), SSDT/PSDT (multiple) - */ - switch (table_type) { - case ACPI_TABLE_ID_DSDT: - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Namespace load: DSDT\n")); - - table_desc = acpi_gbl_table_lists[ACPI_TABLE_ID_DSDT].next; - - /* If table already loaded into namespace, just return */ - - if (table_desc->loaded_into_namespace) { - goto unlock_and_exit; - } - - /* Now load the single DSDT */ - - status = acpi_ns_load_table(table_desc, acpi_gbl_root_node); - if (ACPI_SUCCESS(status)) { - table_desc->loaded_into_namespace = TRUE; - } - break; - - case ACPI_TABLE_ID_SSDT: - case ACPI_TABLE_ID_PSDT: - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Namespace load: %d SSDT or PSDTs\n", - acpi_gbl_table_lists[table_type].count)); - - /* - * Traverse list of SSDT or PSDT tables - */ - table_desc = acpi_gbl_table_lists[table_type].next; - for (i = 0; i < acpi_gbl_table_lists[table_type].count; i++) { - /* - * Only attempt to load table into namespace if it is not - * already loaded! - */ - if (!table_desc->loaded_into_namespace) { - status = - acpi_ns_load_table(table_desc, - acpi_gbl_root_node); - if (ACPI_FAILURE(status)) { - break; - } - - table_desc->loaded_into_namespace = TRUE; - } - - table_desc = table_desc->next; - } - break; - - default: - status = AE_SUPPORT; - break; - } - - unlock_and_exit: - (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); - return_ACPI_STATUS(status); -} - +#ifdef ACPI_OBSOLETE_FUNCTIONS /******************************************************************************* * * FUNCTION: acpi_load_namespace @@ -288,6 +185,7 @@ acpi_status acpi_ns_load_namespace(void) return_ACPI_STATUS(status); } +#endif #ifdef ACPI_FUTURE_IMPLEMENTATION /******************************************************************************* diff --git a/drivers/acpi/namespace/nsparse.c b/drivers/acpi/namespace/nsparse.c index 155505a..2e22479 100644 --- a/drivers/acpi/namespace/nsparse.c +++ b/drivers/acpi/namespace/nsparse.c @@ -45,6 +45,7 @@ #include #include #include +#include #define _COMPONENT ACPI_NAMESPACE ACPI_MODULE_NAME("nsparse") @@ -62,14 +63,24 @@ ACPI_MODULE_NAME("nsparse") * ******************************************************************************/ acpi_status -acpi_ns_one_complete_parse(u8 pass_number, struct acpi_table_desc *table_desc) +acpi_ns_one_complete_parse(acpi_native_uint pass_number, + acpi_native_uint table_index) { union acpi_parse_object *parse_root; acpi_status status; + acpi_native_uint aml_length; + u8 *aml_start; struct acpi_walk_state *walk_state; + struct acpi_table_header *table; + acpi_owner_id owner_id; ACPI_FUNCTION_TRACE(ns_one_complete_parse); + status = acpi_tb_get_owner_id(table_index, &owner_id); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + /* Create and init a Root Node */ parse_root = acpi_ps_create_scope_op(); @@ -79,19 +90,34 @@ acpi_ns_one_complete_parse(u8 pass_number, struct acpi_table_desc *table_desc) /* Create and initialize a new walk state */ - walk_state = acpi_ds_create_walk_state(table_desc->owner_id, - NULL, NULL, NULL); + walk_state = acpi_ds_create_walk_state(owner_id, NULL, NULL, NULL); if (!walk_state) { acpi_ps_free_op(parse_root); return_ACPI_STATUS(AE_NO_MEMORY); } - status = acpi_ds_init_aml_walk(walk_state, parse_root, NULL, - table_desc->aml_start, - table_desc->aml_length, NULL, - pass_number); + status = acpi_get_table_by_index(table_index, &table); + if (ACPI_FAILURE(status)) { + acpi_ds_delete_walk_state(walk_state); + acpi_ps_free_op(parse_root); + return_ACPI_STATUS(status); + } + + /* Table must consist of at least a complete header */ + + if (table->length < sizeof(struct acpi_table_header)) { + status = AE_BAD_HEADER; + } else { + aml_start = (u8 *) table + sizeof(struct acpi_table_header); + aml_length = table->length - sizeof(struct acpi_table_header); + status = acpi_ds_init_aml_walk(walk_state, parse_root, NULL, + aml_start, aml_length, NULL, + (u8) pass_number); + } + if (ACPI_FAILURE(status)) { acpi_ds_delete_walk_state(walk_state); + acpi_ps_delete_parse_tree(parse_root); return_ACPI_STATUS(status); } @@ -119,7 +145,7 @@ acpi_ns_one_complete_parse(u8 pass_number, struct acpi_table_desc *table_desc) ******************************************************************************/ acpi_status -acpi_ns_parse_table(struct acpi_table_desc *table_desc, +acpi_ns_parse_table(acpi_native_uint table_index, struct acpi_namespace_node *start_node) { acpi_status status; @@ -137,7 +163,7 @@ acpi_ns_parse_table(struct acpi_table_desc *table_desc, * performs another complete parse of the AML.. */ ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "**** Start pass 1\n")); - status = acpi_ns_one_complete_parse(1, table_desc); + status = acpi_ns_one_complete_parse(1, table_index); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -152,7 +178,7 @@ acpi_ns_parse_table(struct acpi_table_desc *table_desc, * parse objects are all cached. */ ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "**** Start pass 2\n")); - status = acpi_ns_one_complete_parse(2, table_desc); + status = acpi_ns_one_complete_parse(2, table_index); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } diff --git a/drivers/acpi/namespace/nsutils.c b/drivers/acpi/namespace/nsutils.c index aa4e799..4eb155c 100644 --- a/drivers/acpi/namespace/nsutils.c +++ b/drivers/acpi/namespace/nsutils.c @@ -770,13 +770,6 @@ void acpi_ns_terminate(void) } ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Namespace freed\n")); - - /* - * 2) Now we can delete the ACPI tables - */ - acpi_tb_delete_all_tables(); - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "ACPI Tables freed\n")); - return_VOID; } diff --git a/drivers/acpi/tables/tbconvrt.c b/drivers/acpi/tables/tbconvrt.c deleted file mode 100644 index d697fcb..0000000 --- a/drivers/acpi/tables/tbconvrt.c +++ /dev/null @@ -1,622 +0,0 @@ -/****************************************************************************** - * - * Module Name: tbconvrt - ACPI Table conversion utilities - * - *****************************************************************************/ - -/* - * Copyright (C) 2000 - 2006, R. Byron Moore - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions, and the following disclaimer, - * without modification. - * 2. Redistributions in binary form must reproduce at minimum a disclaimer - * substantially similar to the "NO WARRANTY" disclaimer below - * ("Disclaimer") and any redistribution must be conditioned upon - * including a substantially similar Disclaimer requirement for further - * binary redistribution. - * 3. Neither the names of the above-listed copyright holders nor the names - * of any contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * Alternatively, this software may be distributed under the terms of the - * GNU General Public License ("GPL") version 2 as published by the Free - * Software Foundation. - * - * NO WARRANTY - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING - * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGES. - */ - -#include -#include - -#define _COMPONENT ACPI_TABLES -ACPI_MODULE_NAME("tbconvrt") - -/* Local prototypes */ -static void -acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, - u8 register_bit_width, - acpi_physical_address address); - -static void -acpi_tb_convert_fadt1(struct fadt_descriptor *local_fadt, - struct fadt_descriptor_rev1 *original_fadt); - -static void -acpi_tb_convert_fadt2(struct fadt_descriptor *local_fadt, - struct fadt_descriptor *original_fadt); - -u8 acpi_fadt_is_v1; -ACPI_EXPORT_SYMBOL(acpi_fadt_is_v1) - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_table_count - * - * PARAMETERS: RSDP - Pointer to the RSDP - * RSDT - Pointer to the RSDT/XSDT - * - * RETURN: The number of tables pointed to by the RSDT or XSDT. - * - * DESCRIPTION: Calculate the number of tables. Automatically handles either - * an RSDT or XSDT. - * - ******************************************************************************/ - -u32 -acpi_tb_get_table_count(struct rsdp_descriptor *RSDP, - struct acpi_table_header *RSDT) -{ - u32 pointer_size; - - ACPI_FUNCTION_ENTRY(); - - /* RSDT pointers are 32 bits, XSDT pointers are 64 bits */ - - if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { - pointer_size = sizeof(u32); - } else { - pointer_size = sizeof(u64); - } - - /* - * Determine the number of tables pointed to by the RSDT/XSDT. - * This is defined by the ACPI Specification to be the number of - * pointers contained within the RSDT/XSDT. The size of the pointers - * is architecture-dependent. - */ - return ((RSDT->length - - sizeof(struct acpi_table_header)) / pointer_size); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_convert_to_xsdt - * - * PARAMETERS: table_info - Info about the RSDT - * - * RETURN: Status - * - * DESCRIPTION: Convert an RSDT to an XSDT (internal common format) - * - ******************************************************************************/ - -acpi_status acpi_tb_convert_to_xsdt(struct acpi_table_desc *table_info) -{ - acpi_size table_size; - u32 i; - struct xsdt_descriptor *new_table; - - ACPI_FUNCTION_ENTRY(); - - /* Compute size of the converted XSDT */ - - table_size = ((acpi_size) acpi_gbl_rsdt_table_count * sizeof(u64)) + - sizeof(struct acpi_table_header); - - /* Allocate an XSDT */ - - new_table = ACPI_ALLOCATE_ZEROED(table_size); - if (!new_table) { - return (AE_NO_MEMORY); - } - - /* Copy the header and set the length */ - - ACPI_MEMCPY(new_table, table_info->pointer, - sizeof(struct acpi_table_header)); - new_table->length = (u32) table_size; - - /* Copy the table pointers */ - - for (i = 0; i < acpi_gbl_rsdt_table_count; i++) { - - /* RSDT pointers are 32 bits, XSDT pointers are 64 bits */ - - if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { - ACPI_STORE_ADDRESS(new_table->table_offset_entry[i], - (ACPI_CAST_PTR - (struct rsdt_descriptor, - table_info->pointer))-> - table_offset_entry[i]); - } else { - new_table->table_offset_entry[i] = - (ACPI_CAST_PTR(struct xsdt_descriptor, - table_info->pointer))-> - table_offset_entry[i]; - } - } - - /* Delete the original table (either mapped or in a buffer) */ - - acpi_tb_delete_single_table(table_info); - - /* Point the table descriptor to the new table */ - - table_info->pointer = - ACPI_CAST_PTR(struct acpi_table_header, new_table); - table_info->length = table_size; - table_info->allocation = ACPI_MEM_ALLOCATED; - - return (AE_OK); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_init_generic_address - * - * PARAMETERS: new_gas_struct - GAS struct to be initialized - * register_bit_width - Width of this register - * Address - Address of the register - * - * RETURN: None - * - * DESCRIPTION: Initialize a GAS structure. - * - ******************************************************************************/ - -static void -acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, - u8 register_bit_width, - acpi_physical_address address) -{ - - ACPI_STORE_ADDRESS(new_gas_struct->address, address); - - new_gas_struct->address_space_id = ACPI_ADR_SPACE_SYSTEM_IO; - new_gas_struct->register_bit_width = register_bit_width; - new_gas_struct->register_bit_offset = 0; - new_gas_struct->access_width = 0; -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_convert_fadt1 - * - * PARAMETERS: local_fadt - Pointer to new FADT - * original_fadt - Pointer to old FADT - * - * RETURN: None, populates local_fadt - * - * DESCRIPTION: Convert an ACPI 1.0 FADT to common internal format - * - ******************************************************************************/ - -static void -acpi_tb_convert_fadt1(struct fadt_descriptor *local_fadt, - struct fadt_descriptor_rev1 *original_fadt) -{ - - /* ACPI 1.0 FACS */ - /* The BIOS stored FADT should agree with Revision 1.0 */ - acpi_fadt_is_v1 = 1; - - /* - * Copy the table header and the common part of the tables. - * - * The 2.0 table is an extension of the 1.0 table, so the entire 1.0 - * table can be copied first, then expand some fields to 64 bits. - */ - ACPI_MEMCPY(local_fadt, original_fadt, - sizeof(struct fadt_descriptor_rev1)); - - /* Convert table pointers to 64-bit fields */ - - ACPI_STORE_ADDRESS(local_fadt->xfirmware_ctrl, - local_fadt->V1_firmware_ctrl); - ACPI_STORE_ADDRESS(local_fadt->Xdsdt, local_fadt->V1_dsdt); - - /* - * System Interrupt Model isn't used in ACPI 2.0 - * (local_fadt->Reserved1 = 0;) - */ - - /* - * This field is set by the OEM to convey the preferred power management - * profile to OSPM. It doesn't have any 1.0 equivalence. Since we don't - * know what kind of 32-bit system this is, we will use "unspecified". - */ - local_fadt->prefer_PM_profile = PM_UNSPECIFIED; - - /* - * Processor Performance State Control. This is the value OSPM writes to - * the SMI_CMD register to assume processor performance state control - * responsibility. There isn't any equivalence in 1.0, but as many 1.x - * ACPI tables contain _PCT and _PSS we also keep this value, unless - * acpi_strict is set. - */ - if (acpi_strict) - local_fadt->pstate_cnt = 0; - - /* - * Support for the _CST object and C States change notification. - * This data item hasn't any 1.0 equivalence so leave it zero. - */ - local_fadt->cst_cnt = 0; - - /* - * FADT Rev 2 was an interim FADT released between ACPI 1.0 and ACPI 2.0. - * It primarily adds the FADT reset mechanism. - */ - if ((original_fadt->revision == 2) && - (original_fadt->length == - sizeof(struct fadt_descriptor_rev2_minus))) { - /* - * Grab the entire generic address struct, plus the 1-byte reset value - * that immediately follows. - */ - ACPI_MEMCPY(&local_fadt->reset_register, - &(ACPI_CAST_PTR(struct fadt_descriptor_rev2_minus, - original_fadt))->reset_register, - sizeof(struct acpi_generic_address) + 1); - } else { - /* - * Since there isn't any equivalence in 1.0 and since it is highly - * likely that a 1.0 system has legacy support. - */ - local_fadt->iapc_boot_arch = BAF_LEGACY_DEVICES; - } - - /* - * Convert the V1.0 block addresses to V2.0 GAS structures - */ - acpi_tb_init_generic_address(&local_fadt->xpm1a_evt_blk, - local_fadt->pm1_evt_len, - (acpi_physical_address) local_fadt-> - V1_pm1a_evt_blk); - acpi_tb_init_generic_address(&local_fadt->xpm1b_evt_blk, - local_fadt->pm1_evt_len, - (acpi_physical_address) local_fadt-> - V1_pm1b_evt_blk); - acpi_tb_init_generic_address(&local_fadt->xpm1a_cnt_blk, - local_fadt->pm1_cnt_len, - (acpi_physical_address) local_fadt-> - V1_pm1a_cnt_blk); - acpi_tb_init_generic_address(&local_fadt->xpm1b_cnt_blk, - local_fadt->pm1_cnt_len, - (acpi_physical_address) local_fadt-> - V1_pm1b_cnt_blk); - acpi_tb_init_generic_address(&local_fadt->xpm2_cnt_blk, - local_fadt->pm2_cnt_len, - (acpi_physical_address) local_fadt-> - V1_pm2_cnt_blk); - acpi_tb_init_generic_address(&local_fadt->xpm_tmr_blk, - local_fadt->pm_tm_len, - (acpi_physical_address) local_fadt-> - V1_pm_tmr_blk); - acpi_tb_init_generic_address(&local_fadt->xgpe0_blk, 0, - (acpi_physical_address) local_fadt-> - V1_gpe0_blk); - acpi_tb_init_generic_address(&local_fadt->xgpe1_blk, 0, - (acpi_physical_address) local_fadt-> - V1_gpe1_blk); - - /* Create separate GAS structs for the PM1 Enable registers */ - - acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, - (u8) ACPI_DIV_2(acpi_gbl_FADT-> - pm1_evt_len), - (acpi_physical_address) - (local_fadt->xpm1a_evt_blk.address + - ACPI_DIV_2(acpi_gbl_FADT->pm1_evt_len))); - - /* PM1B is optional; leave null if not present */ - - if (local_fadt->xpm1b_evt_blk.address) { - acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, - (u8) ACPI_DIV_2(acpi_gbl_FADT-> - pm1_evt_len), - (acpi_physical_address) - (local_fadt->xpm1b_evt_blk. - address + - ACPI_DIV_2(acpi_gbl_FADT-> - pm1_evt_len))); - } -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_convert_fadt2 - * - * PARAMETERS: local_fadt - Pointer to new FADT - * original_fadt - Pointer to old FADT - * - * RETURN: None, populates local_fadt - * - * DESCRIPTION: Convert an ACPI 2.0 FADT to common internal format. - * Handles optional "X" fields. - * - ******************************************************************************/ - -static void -acpi_tb_convert_fadt2(struct fadt_descriptor *local_fadt, - struct fadt_descriptor *original_fadt) -{ - - /* We have an ACPI 2.0 FADT but we must copy it to our local buffer */ - - ACPI_MEMCPY(local_fadt, original_fadt, sizeof(struct fadt_descriptor)); - - /* - * "X" fields are optional extensions to the original V1.0 fields, so - * we must selectively expand V1.0 fields if the corresponding X field - * is zero. - */ - if (!(local_fadt->xfirmware_ctrl)) { - ACPI_STORE_ADDRESS(local_fadt->xfirmware_ctrl, - local_fadt->V1_firmware_ctrl); - } - - if (!(local_fadt->Xdsdt)) { - ACPI_STORE_ADDRESS(local_fadt->Xdsdt, local_fadt->V1_dsdt); - } - - if (!(local_fadt->xpm1a_evt_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xpm1a_evt_blk, - local_fadt->pm1_evt_len, - (acpi_physical_address) - local_fadt->V1_pm1a_evt_blk); - } - - if (!(local_fadt->xpm1b_evt_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xpm1b_evt_blk, - local_fadt->pm1_evt_len, - (acpi_physical_address) - local_fadt->V1_pm1b_evt_blk); - } - - if (!(local_fadt->xpm1a_cnt_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xpm1a_cnt_blk, - local_fadt->pm1_cnt_len, - (acpi_physical_address) - local_fadt->V1_pm1a_cnt_blk); - } - - if (!(local_fadt->xpm1b_cnt_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xpm1b_cnt_blk, - local_fadt->pm1_cnt_len, - (acpi_physical_address) - local_fadt->V1_pm1b_cnt_blk); - } - - if (!(local_fadt->xpm2_cnt_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xpm2_cnt_blk, - local_fadt->pm2_cnt_len, - (acpi_physical_address) - local_fadt->V1_pm2_cnt_blk); - } - - if (!(local_fadt->xpm_tmr_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xpm_tmr_blk, - local_fadt->pm_tm_len, - (acpi_physical_address) - local_fadt->V1_pm_tmr_blk); - } - - if (!(local_fadt->xgpe0_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xgpe0_blk, - 0, - (acpi_physical_address) - local_fadt->V1_gpe0_blk); - } - - if (!(local_fadt->xgpe1_blk.address)) { - acpi_tb_init_generic_address(&local_fadt->xgpe1_blk, - 0, - (acpi_physical_address) - local_fadt->V1_gpe1_blk); - } - - /* Create separate GAS structs for the PM1 Enable registers */ - - acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, - (u8) ACPI_DIV_2(acpi_gbl_FADT-> - pm1_evt_len), - (acpi_physical_address) - (local_fadt->xpm1a_evt_blk.address + - ACPI_DIV_2(acpi_gbl_FADT->pm1_evt_len))); - - acpi_gbl_xpm1a_enable.address_space_id = - local_fadt->xpm1a_evt_blk.address_space_id; - - /* PM1B is optional; leave null if not present */ - - if (local_fadt->xpm1b_evt_blk.address) { - acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, - (u8) ACPI_DIV_2(acpi_gbl_FADT-> - pm1_evt_len), - (acpi_physical_address) - (local_fadt->xpm1b_evt_blk. - address + - ACPI_DIV_2(acpi_gbl_FADT-> - pm1_evt_len))); - - acpi_gbl_xpm1b_enable.address_space_id = - local_fadt->xpm1b_evt_blk.address_space_id; - } -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_convert_table_fadt - * - * PARAMETERS: None - * - * RETURN: Status - * - * DESCRIPTION: Converts a BIOS supplied ACPI 1.0 FADT to a local - * ACPI 2.0 FADT. If the BIOS supplied a 2.0 FADT then it is simply - * copied to the local FADT. The ACPI CA software uses this - * local FADT. Thus a significant amount of special #ifdef - * type codeing is saved. - * - ******************************************************************************/ - -acpi_status acpi_tb_convert_table_fadt(void) -{ - struct fadt_descriptor *local_fadt; - struct acpi_table_desc *table_desc; - - ACPI_FUNCTION_TRACE(tb_convert_table_fadt); - - /* - * acpi_gbl_FADT is valid. Validate the FADT length. The table must be - * at least as long as the version 1.0 FADT - */ - if (acpi_gbl_FADT->length < sizeof(struct fadt_descriptor_rev1)) { - ACPI_ERROR((AE_INFO, "FADT is invalid, too short: 0x%X", - acpi_gbl_FADT->length)); - return_ACPI_STATUS(AE_INVALID_TABLE_LENGTH); - } - - /* Allocate buffer for the ACPI 2.0(+) FADT */ - - local_fadt = ACPI_ALLOCATE_ZEROED(sizeof(struct fadt_descriptor)); - if (!local_fadt) { - return_ACPI_STATUS(AE_NO_MEMORY); - } - - if (acpi_gbl_FADT->revision >= FADT2_REVISION_ID) { - if (acpi_gbl_FADT->length < sizeof(struct fadt_descriptor)) { - - /* Length is too short to be a V2.0 table */ - - ACPI_WARNING((AE_INFO, - "Inconsistent FADT length (0x%X) and revision (0x%X), using FADT V1.0 portion of table", - acpi_gbl_FADT->length, - acpi_gbl_FADT->revision)); - - acpi_tb_convert_fadt1(local_fadt, - (void *)acpi_gbl_FADT); - } else { - /* Valid V2.0 table */ - - acpi_tb_convert_fadt2(local_fadt, acpi_gbl_FADT); - } - } else { - /* Valid V1.0 table */ - - acpi_tb_convert_fadt1(local_fadt, (void *)acpi_gbl_FADT); - } - - /* Global FADT pointer will point to the new common V2.0 FADT */ - - acpi_gbl_FADT = local_fadt; - acpi_gbl_FADT->length = sizeof(struct fadt_descriptor); - - /* Free the original table */ - - table_desc = acpi_gbl_table_lists[ACPI_TABLE_ID_FADT].next; - acpi_tb_delete_single_table(table_desc); - - /* Install the new table */ - - table_desc->pointer = - ACPI_CAST_PTR(struct acpi_table_header, acpi_gbl_FADT); - table_desc->allocation = ACPI_MEM_ALLOCATED; - table_desc->length = sizeof(struct fadt_descriptor); - - /* Dump the entire FADT */ - - ACPI_DEBUG_PRINT((ACPI_DB_TABLES, - "Hex dump of common internal FADT, size %d (%X)\n", - acpi_gbl_FADT->length, acpi_gbl_FADT->length)); - - ACPI_DUMP_BUFFER(ACPI_CAST_PTR(u8, acpi_gbl_FADT), - acpi_gbl_FADT->length); - - return_ACPI_STATUS(AE_OK); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_build_common_facs - * - * PARAMETERS: table_info - Info for currently installed FACS - * - * RETURN: Status - * - * DESCRIPTION: Convert ACPI 1.0 and ACPI 2.0 FACS to a common internal - * table format. - * - ******************************************************************************/ - -acpi_status acpi_tb_build_common_facs(struct acpi_table_desc *table_info) -{ - - ACPI_FUNCTION_TRACE(tb_build_common_facs); - - /* Absolute minimum length is 24, but the ACPI spec says 64 */ - - if (acpi_gbl_FACS->length < 24) { - ACPI_ERROR((AE_INFO, "Invalid FACS table length: 0x%X", - acpi_gbl_FACS->length)); - return_ACPI_STATUS(AE_INVALID_TABLE_LENGTH); - } - - if (acpi_gbl_FACS->length < 64) { - ACPI_WARNING((AE_INFO, - "FACS is shorter than the ACPI specification allows: 0x%X, using anyway", - acpi_gbl_FACS->length)); - } - - /* Copy fields to the new FACS */ - - acpi_gbl_common_fACS.global_lock = &(acpi_gbl_FACS->global_lock); - - if ((acpi_gbl_RSDP->revision < 2) || - (acpi_gbl_FACS->length < 32) || - (!(acpi_gbl_FACS->xfirmware_waking_vector))) { - - /* ACPI 1.0 FACS or short table or optional X_ field is zero */ - - acpi_gbl_common_fACS.firmware_waking_vector = ACPI_CAST_PTR(u64, - & - (acpi_gbl_FACS-> - firmware_waking_vector)); - acpi_gbl_common_fACS.vector_width = 32; - } else { - /* ACPI 2.0 FACS with valid X_ field */ - - acpi_gbl_common_fACS.firmware_waking_vector = - &acpi_gbl_FACS->xfirmware_waking_vector; - acpi_gbl_common_fACS.vector_width = 64; - } - - return_ACPI_STATUS(AE_OK); -} diff --git a/drivers/acpi/tables/tbfind.c b/drivers/acpi/tables/tbfind.c new file mode 100644 index 0000000..769213c --- /dev/null +++ b/drivers/acpi/tables/tbfind.c @@ -0,0 +1,126 @@ +/****************************************************************************** + * + * Module Name: tbfind - find table + * + *****************************************************************************/ + +/* + * Copyright (C) 2000 - 2006, R. Byron Moore + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions, and the following disclaimer, + * without modification. + * 2. Redistributions in binary form must reproduce at minimum a disclaimer + * substantially similar to the "NO WARRANTY" disclaimer below + * ("Disclaimer") and any redistribution must be conditioned upon + * including a substantially similar Disclaimer requirement for further + * binary redistribution. + * 3. Neither the names of the above-listed copyright holders nor the names + * of any contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * Alternatively, this software may be distributed under the terms of the + * GNU General Public License ("GPL") version 2 as published by the Free + * Software Foundation. + * + * NO WARRANTY + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + */ + +#include +#include + +#define _COMPONENT ACPI_TABLES +ACPI_MODULE_NAME("tbfind") + +/******************************************************************************* + * + * FUNCTION: acpi_tb_find_table + * + * PARAMETERS: Signature - String with ACPI table signature + * oem_id - String with the table OEM ID + * oem_table_id - String with the OEM Table ID + * table_index - Where the table index is returned + * + * RETURN: Status and table index + * + * DESCRIPTION: Find an ACPI table (in the RSDT/XSDT) that matches the + * Signature, OEM ID and OEM Table ID. Returns an index that can + * be used to get the table header or entire table. + * + ******************************************************************************/ +acpi_status +acpi_tb_find_table(char *signature, + char *oem_id, + char *oem_table_id, acpi_native_uint * table_index) +{ + acpi_native_uint i; + acpi_status status; + + ACPI_FUNCTION_TRACE(tb_find_table); + + for (i = 0; i < acpi_gbl_root_table_list.count; ++i) { + if (ACPI_MEMCMP(&(acpi_gbl_root_table_list.tables[i].signature), + signature, ACPI_NAME_SIZE)) { + + /* Not the requested table */ + + continue; + } + + /* Table with matching signature has been found */ + + if (!acpi_gbl_root_table_list.tables[i].pointer) { + + /* Table is not currently mapped, map it */ + + status = + acpi_tb_verify_table(&acpi_gbl_root_table_list. + tables[i]); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + + if (!acpi_gbl_root_table_list.tables[i].pointer) { + continue; + } + } + + /* Check for table match on all IDs */ + + if (!ACPI_MEMCMP + (acpi_gbl_root_table_list.tables[i].pointer->signature, + signature, ACPI_NAME_SIZE) && (!oem_id[0] + || + !ACPI_MEMCMP + (acpi_gbl_root_table_list. + tables[i].pointer->oem_id, + oem_id, ACPI_OEM_ID_SIZE)) + && (!oem_table_id[0] + || !ACPI_MEMCMP(acpi_gbl_root_table_list.tables[i]. + pointer->oem_table_id, oem_table_id, + ACPI_OEM_TABLE_ID_SIZE))) { + *table_index = i; + + ACPI_DEBUG_PRINT((ACPI_DB_TABLES, + "Found table [%4.4s]\n", signature)); + return_ACPI_STATUS(AE_OK); + } + } + + return_ACPI_STATUS(AE_NOT_FOUND); +} diff --git a/drivers/acpi/tables/tbget.c b/drivers/acpi/tables/tbget.c deleted file mode 100644 index 11e2d44..0000000 --- a/drivers/acpi/tables/tbget.c +++ /dev/null @@ -1,471 +0,0 @@ -/****************************************************************************** - * - * Module Name: tbget - ACPI Table get* routines - * - *****************************************************************************/ - -/* - * Copyright (C) 2000 - 2006, R. Byron Moore - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions, and the following disclaimer, - * without modification. - * 2. Redistributions in binary form must reproduce at minimum a disclaimer - * substantially similar to the "NO WARRANTY" disclaimer below - * ("Disclaimer") and any redistribution must be conditioned upon - * including a substantially similar Disclaimer requirement for further - * binary redistribution. - * 3. Neither the names of the above-listed copyright holders nor the names - * of any contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * Alternatively, this software may be distributed under the terms of the - * GNU General Public License ("GPL") version 2 as published by the Free - * Software Foundation. - * - * NO WARRANTY - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING - * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGES. - */ - -#include -#include - -#define _COMPONENT ACPI_TABLES -ACPI_MODULE_NAME("tbget") - -/* Local prototypes */ -static acpi_status -acpi_tb_get_this_table(struct acpi_pointer *address, - struct acpi_table_header *header, - struct acpi_table_desc *table_info); - -static acpi_status -acpi_tb_table_override(struct acpi_table_header *header, - struct acpi_table_desc *table_info); - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_table - * - * PARAMETERS: Address - Address of table to retrieve. Can be - * Logical or Physical - * table_info - Where table info is returned - * - * RETURN: None - * - * DESCRIPTION: Get entire table of unknown size. - * - ******************************************************************************/ - -acpi_status -acpi_tb_get_table(struct acpi_pointer *address, - struct acpi_table_desc *table_info) -{ - acpi_status status; - struct acpi_table_header header; - - ACPI_FUNCTION_TRACE(tb_get_table); - - /* Get the header in order to get signature and table size */ - - status = acpi_tb_get_table_header(address, &header); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Get the entire table */ - - status = acpi_tb_get_table_body(address, &header, table_info); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "Could not get ACPI table (size %X)", - header.length)); - return_ACPI_STATUS(status); - } - - return_ACPI_STATUS(AE_OK); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_table_header - * - * PARAMETERS: Address - Address of table to retrieve. Can be - * Logical or Physical - * return_header - Where the table header is returned - * - * RETURN: Status - * - * DESCRIPTION: Get an ACPI table header. Works in both physical or virtual - * addressing mode. Works with both physical or logical pointers. - * Table is either copied or mapped, depending on the pointer - * type and mode of the processor. - * - ******************************************************************************/ - -acpi_status -acpi_tb_get_table_header(struct acpi_pointer *address, - struct acpi_table_header *return_header) -{ - acpi_status status = AE_OK; - struct acpi_table_header *header = NULL; - - ACPI_FUNCTION_TRACE(tb_get_table_header); - - /* - * Flags contains the current processor mode (Virtual or Physical - * addressing) The pointer_type is either Logical or Physical - */ - switch (address->pointer_type) { - case ACPI_PHYSMODE_PHYSPTR: - case ACPI_LOGMODE_LOGPTR: - - /* Pointer matches processor mode, copy the header */ - - ACPI_MEMCPY(return_header, address->pointer.logical, - sizeof(struct acpi_table_header)); - break; - - case ACPI_LOGMODE_PHYSPTR: - - /* Create a logical address for the physical pointer */ - - status = acpi_os_map_memory(address->pointer.physical, - sizeof(struct acpi_table_header), - (void *)&header); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, - "Could not map memory at %8.8X%8.8X for table header", - ACPI_FORMAT_UINT64(address->pointer. - physical))); - return_ACPI_STATUS(status); - } - - /* Copy header and delete mapping */ - - ACPI_MEMCPY(return_header, header, - sizeof(struct acpi_table_header)); - acpi_os_unmap_memory(header, sizeof(struct acpi_table_header)); - break; - - default: - - ACPI_ERROR((AE_INFO, "Invalid address flags %X", - address->pointer_type)); - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - ACPI_DEBUG_PRINT((ACPI_DB_TABLES, "Table Signature: [%4.4s]\n", - return_header->signature)); - - return_ACPI_STATUS(AE_OK); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_table_body - * - * PARAMETERS: Address - Address of table to retrieve. Can be - * Logical or Physical - * Header - Header of the table to retrieve - * table_info - Where the table info is returned - * - * RETURN: Status - * - * DESCRIPTION: Get an entire ACPI table with support to allow the host OS to - * replace the table with a newer version (table override.) - * Works in both physical or virtual - * addressing mode. Works with both physical or logical pointers. - * Table is either copied or mapped, depending on the pointer - * type and mode of the processor. - * - ******************************************************************************/ - -acpi_status -acpi_tb_get_table_body(struct acpi_pointer *address, - struct acpi_table_header *header, - struct acpi_table_desc *table_info) -{ - acpi_status status; - - ACPI_FUNCTION_TRACE(tb_get_table_body); - - if (!table_info || !address) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - /* Attempt table override. */ - - status = acpi_tb_table_override(header, table_info); - if (ACPI_SUCCESS(status)) { - - /* Table was overridden by the host OS */ - - return_ACPI_STATUS(status); - } - - /* No override, get the original table */ - - status = acpi_tb_get_this_table(address, header, table_info); - return_ACPI_STATUS(status); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_table_override - * - * PARAMETERS: Header - Pointer to table header - * table_info - Return info if table is overridden - * - * RETURN: None - * - * DESCRIPTION: Attempts override of current table with a new one if provided - * by the host OS. - * - ******************************************************************************/ - -static acpi_status -acpi_tb_table_override(struct acpi_table_header *header, - struct acpi_table_desc *table_info) -{ - struct acpi_table_header *new_table; - acpi_status status; - struct acpi_pointer address; - - ACPI_FUNCTION_TRACE(tb_table_override); - - /* - * The OSL will examine the header and decide whether to override this - * table. If it decides to override, a table will be returned in new_table, - * which we will then copy. - */ - status = acpi_os_table_override(header, &new_table); - if (ACPI_FAILURE(status)) { - - /* Some severe error from the OSL, but we basically ignore it */ - - ACPI_EXCEPTION((AE_INFO, status, - "Could not override ACPI table")); - return_ACPI_STATUS(status); - } - - if (!new_table) { - - /* No table override */ - - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - - /* - * We have a new table to override the old one. Get a copy of - * the new one. We know that the new table has a logical pointer. - */ - address.pointer_type = ACPI_LOGICAL_POINTER | ACPI_LOGICAL_ADDRESSING; - address.pointer.logical = new_table; - - status = acpi_tb_get_this_table(&address, new_table, table_info); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, "Could not copy ACPI table")); - return_ACPI_STATUS(status); - } - - /* Copy the table info */ - - ACPI_INFO((AE_INFO, "Table [%4.4s] replaced by host OS", - table_info->pointer->signature)); - - return_ACPI_STATUS(AE_OK); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_this_table - * - * PARAMETERS: Address - Address of table to retrieve. Can be - * Logical or Physical - * Header - Header of the table to retrieve - * table_info - Where the table info is returned - * - * RETURN: Status - * - * DESCRIPTION: Get an entire ACPI table. Works in both physical or virtual - * addressing mode. Works with both physical or logical pointers. - * Table is either copied or mapped, depending on the pointer - * type and mode of the processor. - * - ******************************************************************************/ - -static acpi_status -acpi_tb_get_this_table(struct acpi_pointer *address, - struct acpi_table_header *header, - struct acpi_table_desc *table_info) -{ - struct acpi_table_header *full_table = NULL; - u8 allocation; - acpi_status status = AE_OK; - - ACPI_FUNCTION_TRACE(tb_get_this_table); - - /* Validate minimum length */ - - if (header->length < sizeof(struct acpi_table_header)) { - ACPI_ERROR((AE_INFO, - "Table length (%X) is smaller than minimum (%zX)", - header->length, sizeof(struct acpi_table_header))); - - return_ACPI_STATUS(AE_INVALID_TABLE_LENGTH); - } - - /* - * Flags contains the current processor mode (Virtual or Physical - * addressing) The pointer_type is either Logical or Physical - */ - switch (address->pointer_type) { - case ACPI_PHYSMODE_PHYSPTR: - case ACPI_LOGMODE_LOGPTR: - - /* Pointer matches processor mode, copy the table to a new buffer */ - - full_table = ACPI_ALLOCATE(header->length); - if (!full_table) { - ACPI_ERROR((AE_INFO, - "Could not allocate table memory for [%4.4s] length %X", - header->signature, header->length)); - return_ACPI_STATUS(AE_NO_MEMORY); - } - - /* Copy the entire table (including header) to the local buffer */ - - ACPI_MEMCPY(full_table, address->pointer.logical, - header->length); - - /* Save allocation type */ - - allocation = ACPI_MEM_ALLOCATED; - break; - - case ACPI_LOGMODE_PHYSPTR: - - /* - * Just map the table's physical memory - * into our address space. - */ - status = acpi_os_map_memory(address->pointer.physical, - (acpi_size) header->length, - ACPI_CAST_PTR(void, &full_table)); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, - "Could not map memory for table [%4.4s] at %8.8X%8.8X for length %X", - header->signature, - ACPI_FORMAT_UINT64(address->pointer. - physical), - header->length)); - return (status); - } - - /* Save allocation type */ - - allocation = ACPI_MEM_MAPPED; - break; - - default: - - ACPI_ERROR((AE_INFO, "Invalid address flags %X", - address->pointer_type)); - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - /* - * Validate checksum for _most_ tables, - * even the ones whose signature we don't recognize - */ - if (table_info->type != ACPI_TABLE_ID_FACS) { - status = acpi_tb_verify_table_checksum(full_table); - -#if (!ACPI_CHECKSUM_ABORT) - if (ACPI_FAILURE(status)) { - - /* Ignore the error if configuration says so */ - - status = AE_OK; - } -#endif - } - - /* Return values */ - - table_info->pointer = full_table; - table_info->length = (acpi_size) header->length; - table_info->allocation = allocation; - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Found table [%4.4s] at %8.8X%8.8X, mapped/copied to %p\n", - full_table->signature, - ACPI_FORMAT_UINT64(address->pointer.physical), - full_table)); - - return_ACPI_STATUS(status); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_table_ptr - * - * PARAMETERS: table_type - one of the defined table types - * Instance - Which table of this type - * return_table - pointer to location to place the pointer for - * return - * - * RETURN: Status - * - * DESCRIPTION: This function is called to get the pointer to an ACPI table. - * - ******************************************************************************/ - -acpi_status -acpi_tb_get_table_ptr(acpi_table_type table_type, - u32 instance, struct acpi_table_header **return_table) -{ - struct acpi_table_desc *table_desc; - u32 i; - - ACPI_FUNCTION_TRACE(tb_get_table_ptr); - - if (table_type > ACPI_TABLE_ID_MAX) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - /* Check for instance out of range of the current table count */ - - if (instance > acpi_gbl_table_lists[table_type].count) { - return_ACPI_STATUS(AE_NOT_EXIST); - } - - /* - * Walk the list to get the desired table - * Note: Instance is one-based - */ - table_desc = acpi_gbl_table_lists[table_type].next; - for (i = 1; i < instance; i++) { - table_desc = table_desc->next; - } - - /* We are now pointing to the requested table's descriptor */ - - *return_table = table_desc->pointer; - return_ACPI_STATUS(AE_OK); -} diff --git a/drivers/acpi/tables/tbgetall.c b/drivers/acpi/tables/tbgetall.c deleted file mode 100644 index ad98211..0000000 --- a/drivers/acpi/tables/tbgetall.c +++ /dev/null @@ -1,311 +0,0 @@ -/****************************************************************************** - * - * Module Name: tbgetall - Get all required ACPI tables - * - *****************************************************************************/ - -/* - * Copyright (C) 2000 - 2006, R. Byron Moore - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions, and the following disclaimer, - * without modification. - * 2. Redistributions in binary form must reproduce at minimum a disclaimer - * substantially similar to the "NO WARRANTY" disclaimer below - * ("Disclaimer") and any redistribution must be conditioned upon - * including a substantially similar Disclaimer requirement for further - * binary redistribution. - * 3. Neither the names of the above-listed copyright holders nor the names - * of any contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * Alternatively, this software may be distributed under the terms of the - * GNU General Public License ("GPL") version 2 as published by the Free - * Software Foundation. - * - * NO WARRANTY - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING - * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGES. - */ - -#include -#include - -#define _COMPONENT ACPI_TABLES -ACPI_MODULE_NAME("tbgetall") - -/* Local prototypes */ -static acpi_status -acpi_tb_get_primary_table(struct acpi_pointer *address, - struct acpi_table_desc *table_info); - -static acpi_status -acpi_tb_get_secondary_table(struct acpi_pointer *address, - acpi_string signature, - struct acpi_table_desc *table_info); - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_primary_table - * - * PARAMETERS: Address - Physical address of table to retrieve - * *table_info - Where the table info is returned - * - * RETURN: Status - * - * DESCRIPTION: Maps the physical address of table into a logical address - * - ******************************************************************************/ - -static acpi_status -acpi_tb_get_primary_table(struct acpi_pointer *address, - struct acpi_table_desc *table_info) -{ - acpi_status status; - struct acpi_table_header header; - - ACPI_FUNCTION_TRACE(tb_get_primary_table); - - /* Ignore a NULL address in the RSDT */ - - if (!address->pointer.value) { - return_ACPI_STATUS(AE_OK); - } - - /* Get the header in order to get signature and table size */ - - status = acpi_tb_get_table_header(address, &header); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Clear the table_info */ - - ACPI_MEMSET(table_info, 0, sizeof(struct acpi_table_desc)); - - /* - * Check the table signature and make sure it is recognized. - * Also checks the header checksum - */ - table_info->pointer = &header; - status = acpi_tb_recognize_table(table_info, ACPI_TABLE_PRIMARY); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Get the entire table */ - - status = acpi_tb_get_table_body(address, &header, table_info); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Install the table */ - - status = acpi_tb_install_table(table_info); - return_ACPI_STATUS(status); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_secondary_table - * - * PARAMETERS: Address - Physical address of table to retrieve - * *table_info - Where the table info is returned - * - * RETURN: Status - * - * DESCRIPTION: Maps the physical address of table into a logical address - * - ******************************************************************************/ - -static acpi_status -acpi_tb_get_secondary_table(struct acpi_pointer *address, - acpi_string signature, - struct acpi_table_desc *table_info) -{ - acpi_status status; - struct acpi_table_header header; - - ACPI_FUNCTION_TRACE_STR(tb_get_secondary_table, signature); - - /* Get the header in order to match the signature */ - - status = acpi_tb_get_table_header(address, &header); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Signature must match request */ - - if (!ACPI_COMPARE_NAME(header.signature, signature)) { - ACPI_ERROR((AE_INFO, - "Incorrect table signature - wanted [%s] found [%4.4s]", - signature, header.signature)); - return_ACPI_STATUS(AE_BAD_SIGNATURE); - } - - /* - * Check the table signature and make sure it is recognized. - * Also checks the header checksum - */ - table_info->pointer = &header; - status = acpi_tb_recognize_table(table_info, ACPI_TABLE_SECONDARY); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Get the entire table */ - - status = acpi_tb_get_table_body(address, &header, table_info); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Install the table */ - - status = acpi_tb_install_table(table_info); - return_ACPI_STATUS(status); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_required_tables - * - * PARAMETERS: None - * - * RETURN: Status - * - * DESCRIPTION: Load and validate tables other than the RSDT. The RSDT must - * already be loaded and validated. - * - * Get the minimum set of ACPI tables, namely: - * - * 1) FADT (via RSDT in loop below) - * 2) FACS (via FADT) - * 3) DSDT (via FADT) - * - ******************************************************************************/ - -acpi_status acpi_tb_get_required_tables(void) -{ - acpi_status status = AE_OK; - u32 i; - struct acpi_table_desc table_info; - struct acpi_pointer address; - - ACPI_FUNCTION_TRACE(tb_get_required_tables); - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "%d ACPI tables in RSDT\n", - acpi_gbl_rsdt_table_count)); - - address.pointer_type = acpi_gbl_table_flags | ACPI_LOGICAL_ADDRESSING; - - /* - * Loop through all table pointers found in RSDT. - * This will NOT include the FACS and DSDT - we must get - * them after the loop. - * - * The only tables we are interested in getting here is the FADT and - * any SSDTs. - */ - for (i = 0; i < acpi_gbl_rsdt_table_count; i++) { - - /* Get the table address from the common internal XSDT */ - - address.pointer.value = acpi_gbl_XSDT->table_offset_entry[i]; - - /* - * Get the tables needed by this subsystem (FADT and any SSDTs). - * NOTE: All other tables are completely ignored at this time. - */ - status = acpi_tb_get_primary_table(&address, &table_info); - if ((status != AE_OK) && (status != AE_TABLE_NOT_SUPPORTED)) { - ACPI_WARNING((AE_INFO, - "%s, while getting table at %8.8X%8.8X", - acpi_format_exception(status), - ACPI_FORMAT_UINT64(address.pointer. - value))); - } - } - - /* We must have a FADT to continue */ - - if (!acpi_gbl_FADT) { - ACPI_ERROR((AE_INFO, "No FADT present in RSDT/XSDT")); - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - - /* - * Convert the FADT to a common format. This allows earlier revisions of - * the table to coexist with newer versions, using common access code. - */ - status = acpi_tb_convert_table_fadt(); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, - "Could not convert FADT to internal common format")); - return_ACPI_STATUS(status); - } - - /* Get the FACS (Pointed to by the FADT) */ - - address.pointer.value = acpi_gbl_FADT->xfirmware_ctrl; - - status = acpi_tb_get_secondary_table(&address, FACS_SIG, &table_info); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "Could not get/install the FACS")); - return_ACPI_STATUS(status); - } - - /* - * Create the common FACS pointer table - * (Contains pointers to the original table) - */ - status = acpi_tb_build_common_facs(&table_info); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Get/install the DSDT (Pointed to by the FADT) */ - - address.pointer.value = acpi_gbl_FADT->Xdsdt; - - status = acpi_tb_get_secondary_table(&address, DSDT_SIG, &table_info); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, "Could not get/install the DSDT")); - return_ACPI_STATUS(status); - } - - /* Set Integer Width (32/64) based upon DSDT revision */ - - acpi_ut_set_integer_width(acpi_gbl_DSDT->revision); - - /* Dump the entire DSDT */ - - ACPI_DEBUG_PRINT((ACPI_DB_TABLES, - "Hex dump of entire DSDT, size %d (0x%X), Integer width = %d\n", - acpi_gbl_DSDT->length, acpi_gbl_DSDT->length, - acpi_gbl_integer_bit_width)); - - ACPI_DUMP_BUFFER(ACPI_CAST_PTR(u8, acpi_gbl_DSDT), - acpi_gbl_DSDT->length); - - /* Always delete the RSDP mapping, we are done with it */ - - acpi_tb_delete_tables_by_type(ACPI_TABLE_ID_RSDP); - return_ACPI_STATUS(status); -} diff --git a/drivers/acpi/tables/tbinstal.c b/drivers/acpi/tables/tbinstal.c index 1668a23..9076ca0 100644 --- a/drivers/acpi/tables/tbinstal.c +++ b/drivers/acpi/tables/tbinstal.c @@ -42,510 +42,494 @@ */ #include +#include #include #define _COMPONENT ACPI_TABLES ACPI_MODULE_NAME("tbinstal") -/* Local prototypes */ -static acpi_status -acpi_tb_match_signature(char *signature, - struct acpi_table_desc *table_info, u8 search_type); - -/******************************************************************************* +/****************************************************************************** * - * FUNCTION: acpi_tb_match_signature + * FUNCTION: acpi_tb_verify_table * - * PARAMETERS: Signature - Table signature to match - * table_info - Return data - * search_type - Table type to match (primary/secondary) + * PARAMETERS: table_desc - table * * RETURN: Status * - * DESCRIPTION: Compare signature against the list of "ACPI-subsystem-owned" - * tables (DSDT/FADT/SSDT, etc.) Returns the table_type_iD on match. + * DESCRIPTION: this function is called to verify and map table * - ******************************************************************************/ - -static acpi_status -acpi_tb_match_signature(char *signature, - struct acpi_table_desc *table_info, u8 search_type) + *****************************************************************************/ +acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc) { - acpi_native_uint i; + u8 checksum; - ACPI_FUNCTION_TRACE(tb_match_signature); + ACPI_FUNCTION_TRACE(tb_verify_table); - /* Search for a signature match among the known table types */ + /* Map the table if necessary */ - for (i = 0; i < (ACPI_TABLE_ID_MAX + 1); i++) { - if (!(acpi_gbl_table_data[i].flags & search_type)) { - continue; + if (!table_desc->pointer) { + table_desc->pointer = + acpi_tb_map(table_desc->address, table_desc->length, + table_desc->flags & ACPI_TABLE_ORIGIN_MASK); + if (!table_desc->pointer) { + return_ACPI_STATUS(AE_NO_MEMORY); } + } - if (!ACPI_STRNCMP(signature, acpi_gbl_table_data[i].signature, - acpi_gbl_table_data[i].sig_length)) { + /* FACS is the odd table, has no standard ACPI header and no checksum */ - /* Found a signature match, return index if requested */ + if (ACPI_COMPARE_NAME(&(table_desc->signature), ACPI_SIG_FACS)) { + return_ACPI_STATUS(AE_OK); + } - if (table_info) { - table_info->type = (u8) i; - } + /* Always calculate checksum, ignore bad checksum if requested */ - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Table [%4.4s] is an ACPI table consumed by the core subsystem\n", - (char *)acpi_gbl_table_data[i]. - signature)); + checksum = acpi_tb_checksum(ACPI_CAST_PTR(void, table_desc->pointer), + table_desc->length); - return_ACPI_STATUS(AE_OK); - } - } +#if (ACPI_CHECKSUM_ABORT) - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Table [%4.4s] is not an ACPI table consumed by the core subsystem - ignored\n", - (char *)signature)); + if (checksum) { + return_ACPI_STATUS(AE_BAD_CHECKSUM); + } +#endif - return_ACPI_STATUS(AE_TABLE_NOT_SUPPORTED); + return_ACPI_STATUS(AE_OK); } /******************************************************************************* * - * FUNCTION: acpi_tb_install_table + * FUNCTION: acpi_tb_add_table * - * PARAMETERS: table_info - Return value from acpi_tb_get_table_body + * PARAMETERS: Table - Pointer to the table header + * table_index - Where the table index is returned * * RETURN: Status * - * DESCRIPTION: Install the table into the global data structures. + * DESCRIPTION: This function is called to add the ACPI table * ******************************************************************************/ -acpi_status acpi_tb_install_table(struct acpi_table_desc *table_info) +acpi_status +acpi_tb_add_table(struct acpi_table_header *table, + acpi_native_uint * table_index) { - acpi_status status; + acpi_native_uint i; + acpi_native_uint length; + acpi_status status = AE_OK; - ACPI_FUNCTION_TRACE(tb_install_table); + ACPI_FUNCTION_TRACE(tb_add_table); - /* Lock tables while installing */ + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); - status = acpi_ut_acquire_mutex(ACPI_MTX_TABLES); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "Could not acquire table mutex")); - return_ACPI_STATUS(status); + /* Check if table is already registered */ + + for (i = 0; i < acpi_gbl_root_table_list.count; ++i) { + if (!acpi_gbl_root_table_list.tables[i].pointer) { + status = + acpi_tb_verify_table(&acpi_gbl_root_table_list. + tables[i]); + if (ACPI_FAILURE(status) + || !acpi_gbl_root_table_list.tables[i].pointer) { + continue; + } + } + + length = ACPI_MIN(table->length, + acpi_gbl_root_table_list.tables[i].pointer-> + length); + if (ACPI_MEMCMP + (table, acpi_gbl_root_table_list.tables[i].pointer, + length)) { + continue; + } + + /* Table is already registered */ + + ACPI_FREE(table); + *table_index = i; + goto release; } /* - * Ignore a table that is already installed. For example, some BIOS - * ASL code will repeatedly attempt to load the same SSDT. + * Add the table to the global table list */ - status = acpi_tb_is_table_installed(table_info); + status = acpi_tb_store_table(ACPI_TO_INTEGER(table), + table, table->length, + ACPI_TABLE_ORIGIN_ALLOCATED, table_index); if (ACPI_FAILURE(status)) { - goto unlock_and_exit; + goto release; } - /* Install the table into the global data structure */ + acpi_tb_print_table_header(0, table); - status = acpi_tb_init_table_descriptor(table_info->type, table_info); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "Could not install table [%4.4s]", - table_info->pointer->signature)); - } - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "%s located at %p\n", - acpi_gbl_table_data[table_info->type].name, - table_info->pointer)); - - unlock_and_exit: + release: (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); return_ACPI_STATUS(status); } /******************************************************************************* * - * FUNCTION: acpi_tb_recognize_table + * FUNCTION: acpi_tb_resize_root_table_list * - * PARAMETERS: table_info - Return value from acpi_tb_get_table_body - * search_type - Table type to match (primary/secondary) + * PARAMETERS: None * * RETURN: Status * - * DESCRIPTION: Check a table signature for a match against known table types - * - * NOTE: All table pointers are validated as follows: - * 1) Table pointer must point to valid physical memory - * 2) Signature must be 4 ASCII chars, even if we don't recognize the - * name - * 3) Table must be readable for length specified in the header - * 4) Table checksum must be valid (with the exception of the FACS - * which has no checksum for some odd reason) + * DESCRIPTION: Expand the size of global table array * ******************************************************************************/ -acpi_status -acpi_tb_recognize_table(struct acpi_table_desc *table_info, u8 search_type) +acpi_status acpi_tb_resize_root_table_list(void) { - struct acpi_table_header *table_header; - acpi_status status; + struct acpi_table_desc *tables; - ACPI_FUNCTION_TRACE(tb_recognize_table); + ACPI_FUNCTION_TRACE(tb_resize_root_table_list); - /* Ensure that we have a valid table pointer */ + /* allow_resize flag is a parameter to acpi_initialize_tables */ - table_header = (struct acpi_table_header *)table_info->pointer; - if (!table_header) { - return_ACPI_STATUS(AE_BAD_PARAMETER); + if (!(acpi_gbl_root_table_list.flags & ACPI_TABLE_FLAGS_ALLOW_RESIZE)) { + ACPI_ERROR((AE_INFO, + "Resize of Root Table Array is not allowed")); + return_ACPI_STATUS(AE_SUPPORT); } - /* - * We only "recognize" a limited number of ACPI tables -- namely, the - * ones that are used by the subsystem (DSDT, FADT, etc.) - * - * An AE_TABLE_NOT_SUPPORTED means that the table was not recognized. - * This can be any one of many valid ACPI tables, it just isn't one of - * the tables that is consumed by the core subsystem - */ - status = acpi_tb_match_signature(table_header->signature, - table_info, search_type); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + /* Increase the Table Array size */ + + tables = ACPI_ALLOCATE_ZEROED((acpi_gbl_root_table_list.size + + ACPI_ROOT_TABLE_SIZE_INCREMENT) + * sizeof(struct acpi_table_desc)); + if (!tables) { + ACPI_ERROR((AE_INFO, + "Could not allocate new root table array")); + return_ACPI_STATUS(AE_NO_MEMORY); } - status = acpi_tb_validate_table_header(table_header); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + /* Copy and free the previous table array */ + + if (acpi_gbl_root_table_list.tables) { + ACPI_MEMCPY(tables, acpi_gbl_root_table_list.tables, + acpi_gbl_root_table_list.size * + sizeof(struct acpi_table_desc)); + + if (acpi_gbl_root_table_list.flags & ACPI_TABLE_ORIGIN_MASK == + ACPI_TABLE_ORIGIN_ALLOCATED) { + ACPI_FREE(acpi_gbl_root_table_list.tables); + } } - /* Return the table type and length via the info struct */ + acpi_gbl_root_table_list.tables = tables; + acpi_gbl_root_table_list.size += ACPI_ROOT_TABLE_SIZE_INCREMENT; + acpi_gbl_root_table_list.flags = (u8) (ACPI_TABLE_ORIGIN_ALLOCATED | + (acpi_gbl_root_table_list. + flags & + ~ACPI_TABLE_ORIGIN_MASK)); - table_info->length = (acpi_size) table_header->length; - return_ACPI_STATUS(status); + return_ACPI_STATUS(AE_OK); } /******************************************************************************* * - * FUNCTION: acpi_tb_init_table_descriptor + * FUNCTION: acpi_tb_store_table * - * PARAMETERS: table_type - The type of the table - * table_info - A table info struct + * PARAMETERS: Address - Table address + * Table - Table header + * Length - Table length + * Flags - flags * - * RETURN: None. + * RETURN: Status and table index. * - * DESCRIPTION: Install a table into the global data structs. + * DESCRIPTION: Add an ACPI table to the global table list * ******************************************************************************/ acpi_status -acpi_tb_init_table_descriptor(acpi_table_type table_type, - struct acpi_table_desc *table_info) +acpi_tb_store_table(acpi_physical_address address, + struct acpi_table_header *table, + u32 length, u8 flags, acpi_native_uint * table_index) { - struct acpi_table_list *list_head; - struct acpi_table_desc *table_desc; - acpi_status status; - - ACPI_FUNCTION_TRACE_U32(tb_init_table_descriptor, table_type); - - /* Allocate a descriptor for this table */ + acpi_status status = AE_OK; - table_desc = ACPI_ALLOCATE_ZEROED(sizeof(struct acpi_table_desc)); - if (!table_desc) { - return_ACPI_STATUS(AE_NO_MEMORY); - } - - /* Get a new owner ID for the table */ + /* Ensure that there is room for the table in the Root Table List */ - status = acpi_ut_allocate_owner_id(&table_desc->owner_id); - if (ACPI_FAILURE(status)) { - goto error_exit1; + if (acpi_gbl_root_table_list.count >= acpi_gbl_root_table_list.size) { + status = acpi_tb_resize_root_table_list(); + if (ACPI_FAILURE(status)) { + return (status); + } } - /* Install the table into the global data structure */ - - list_head = &acpi_gbl_table_lists[table_type]; + /* Initialize added table */ + + acpi_gbl_root_table_list.tables[acpi_gbl_root_table_list.count]. + address = address; + acpi_gbl_root_table_list.tables[acpi_gbl_root_table_list.count]. + pointer = table; + acpi_gbl_root_table_list.tables[acpi_gbl_root_table_list.count].length = + length; + acpi_gbl_root_table_list.tables[acpi_gbl_root_table_list.count]. + owner_id = 0; + acpi_gbl_root_table_list.tables[acpi_gbl_root_table_list.count].flags = + flags; + + ACPI_MOVE_32_TO_32(& + (acpi_gbl_root_table_list. + tables[acpi_gbl_root_table_list.count].signature), + table->signature); + + *table_index = acpi_gbl_root_table_list.count; + acpi_gbl_root_table_list.count++; + return (status); +} - /* - * Two major types of tables: 1) Only one instance is allowed. This - * includes most ACPI tables such as the DSDT. 2) Multiple instances of - * the table are allowed. This includes SSDT and PSDTs. - */ - if (ACPI_IS_SINGLE_TABLE(acpi_gbl_table_data[table_type].flags)) { - /* - * Only one table allowed, and a table has alread been installed - * at this location, so return an error. - */ - if (list_head->next) { - status = AE_ALREADY_EXISTS; - goto error_exit2; - } +/******************************************************************************* + * + * FUNCTION: acpi_tb_delete_table + * + * PARAMETERS: table_index - Table index + * + * RETURN: None + * + * DESCRIPTION: Delete one internal ACPI table + * + ******************************************************************************/ - table_desc->next = list_head->next; - list_head->next = table_desc; +void acpi_tb_delete_table(acpi_native_uint table_index) +{ + struct acpi_table_desc *table_desc; - if (table_desc->next) { - table_desc->next->prev = table_desc; - } + /* table_index assumed valid */ - list_head->count++; - } else { - /* - * Link the new table in to the list of tables of this type. - * Insert at the end of the list, order IS IMPORTANT. - * - * table_desc->Prev & Next are already NULL from calloc() - */ - list_head->count++; - - if (!list_head->next) { - list_head->next = table_desc; - } else { - table_desc->next = list_head->next; + table_desc = &acpi_gbl_root_table_list.tables[table_index]; - while (table_desc->next->next) { - table_desc->next = table_desc->next->next; - } + /* Table must be mapped or allocated */ - table_desc->next->next = table_desc; - table_desc->prev = table_desc->next; - table_desc->next = NULL; - } + if (!table_desc->pointer) { + return; } - /* Finish initialization of the table descriptor */ - - table_desc->loaded_into_namespace = FALSE; - table_desc->type = (u8) table_type; - table_desc->pointer = table_info->pointer; - table_desc->length = table_info->length; - table_desc->allocation = table_info->allocation; - table_desc->aml_start = (u8 *) (table_desc->pointer + 1), - table_desc->aml_length = (u32) - (table_desc->length - (u32) sizeof(struct acpi_table_header)); - - /* - * Set the appropriate global pointer (if there is one) to point to the - * newly installed table - */ - if (acpi_gbl_table_data[table_type].global_ptr) { - *(acpi_gbl_table_data[table_type].global_ptr) = - table_info->pointer; + if (table_desc->flags & ACPI_TABLE_ORIGIN_MAPPED) { + acpi_tb_unmap(table_desc->pointer, table_desc->length, + table_desc->flags & ACPI_TABLE_ORIGIN_MASK); + } else if (table_desc->flags & ACPI_TABLE_ORIGIN_ALLOCATED) { + ACPI_FREE(table_desc->pointer); } - /* Return Data */ - - table_info->owner_id = table_desc->owner_id; - table_info->installed_desc = table_desc; - return_ACPI_STATUS(AE_OK); - - /* Error exit with cleanup */ - - error_exit2: - - acpi_ut_release_owner_id(&table_desc->owner_id); - - error_exit1: - - ACPI_FREE(table_desc); - return_ACPI_STATUS(status); + table_desc->pointer = NULL; } /******************************************************************************* * - * FUNCTION: acpi_tb_delete_all_tables + * FUNCTION: acpi_tb_terminate * - * PARAMETERS: None. + * PARAMETERS: None * - * RETURN: None. + * RETURN: None * * DESCRIPTION: Delete all internal ACPI tables * ******************************************************************************/ -void acpi_tb_delete_all_tables(void) +void acpi_tb_terminate(void) { - acpi_table_type type; + acpi_native_uint i; + + ACPI_FUNCTION_TRACE(tb_terminate); + + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + + /* Delete the individual tables */ + + for (i = 0; i < acpi_gbl_root_table_list.count; ++i) { + acpi_tb_delete_table(i); + } /* - * Free memory allocated for ACPI tables - * Memory can either be mapped or allocated + * Delete the root table array if allocated locally. Array cannot be + * mapped, so we don't need to check for that flag. */ - for (type = 0; type < (ACPI_TABLE_ID_MAX + 1); type++) { - acpi_tb_delete_tables_by_type(type); + if ((acpi_gbl_root_table_list.flags & ACPI_TABLE_ORIGIN_MASK) == + ACPI_TABLE_ORIGIN_ALLOCATED) { + ACPI_FREE(acpi_gbl_root_table_list.tables); } + + acpi_gbl_root_table_list.tables = NULL; + acpi_gbl_root_table_list.flags = 0; + acpi_gbl_root_table_list.count = 0; + + ACPI_DEBUG_PRINT((ACPI_DB_INFO, "ACPI Tables freed\n")); + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); } /******************************************************************************* * - * FUNCTION: acpi_tb_delete_tables_by_type + * FUNCTION: acpi_tb_delete_namespace_by_owner * - * PARAMETERS: Type - The table type to be deleted + * PARAMETERS: table_index - Table index * - * RETURN: None. + * RETURN: None * - * DESCRIPTION: Delete an internal ACPI table - * Locks the ACPI table mutex + * DESCRIPTION: Delete all namespace objects created when this table was loaded. * ******************************************************************************/ -void acpi_tb_delete_tables_by_type(acpi_table_type type) +void acpi_tb_delete_namespace_by_owner(acpi_native_uint table_index) { - struct acpi_table_desc *table_desc; - u32 count; - u32 i; - - ACPI_FUNCTION_TRACE_U32(tb_delete_tables_by_type, type); - - if (type > ACPI_TABLE_ID_MAX) { - return_VOID; - } + acpi_owner_id owner_id; - if (ACPI_FAILURE(acpi_ut_acquire_mutex(ACPI_MTX_TABLES))) { + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + if (table_index < acpi_gbl_root_table_list.count) { + owner_id = + acpi_gbl_root_table_list.tables[table_index].owner_id; + } else { + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); return; } - /* Clear the appropriate "typed" global table pointer */ - - switch (type) { - case ACPI_TABLE_ID_RSDP: - acpi_gbl_RSDP = NULL; - break; - - case ACPI_TABLE_ID_DSDT: - acpi_gbl_DSDT = NULL; - break; - - case ACPI_TABLE_ID_FADT: - acpi_gbl_FADT = NULL; - break; - - case ACPI_TABLE_ID_FACS: - acpi_gbl_FACS = NULL; - break; + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + acpi_ns_delete_namespace_by_owner(owner_id); +} - case ACPI_TABLE_ID_XSDT: - acpi_gbl_XSDT = NULL; - break; +/******************************************************************************* + * + * FUNCTION: acpi_tb_allocate_owner_id + * + * PARAMETERS: table_index - Table index + * + * RETURN: Status + * + * DESCRIPTION: Allocates owner_id in table_desc + * + ******************************************************************************/ - case ACPI_TABLE_ID_SSDT: - case ACPI_TABLE_ID_PSDT: - default: - break; - } +acpi_status acpi_tb_allocate_owner_id(acpi_native_uint table_index) +{ + acpi_status status = AE_BAD_PARAMETER; - /* - * Free the table - * 1) Get the head of the list - */ - table_desc = acpi_gbl_table_lists[type].next; - count = acpi_gbl_table_lists[type].count; + ACPI_FUNCTION_TRACE(tb_allocate_owner_id); - /* - * 2) Walk the entire list, deleting both the allocated tables - * and the table descriptors - */ - for (i = 0; i < count; i++) { - table_desc = acpi_tb_uninstall_table(table_desc); + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + if (table_index < acpi_gbl_root_table_list.count) { + status = acpi_ut_allocate_owner_id + (&(acpi_gbl_root_table_list.tables[table_index].owner_id)); } (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); - return_VOID; + return_ACPI_STATUS(status); } /******************************************************************************* * - * FUNCTION: acpi_tb_delete_single_table + * FUNCTION: acpi_tb_release_owner_id * - * PARAMETERS: table_info - A table info struct + * PARAMETERS: table_index - Table index * - * RETURN: None. + * RETURN: Status * - * DESCRIPTION: Low-level free for a single ACPI table. Handles cases where - * the table was allocated a buffer or was mapped. + * DESCRIPTION: Releases owner_id in table_desc * ******************************************************************************/ -void acpi_tb_delete_single_table(struct acpi_table_desc *table_desc) +acpi_status acpi_tb_release_owner_id(acpi_native_uint table_index) { + acpi_status status = AE_BAD_PARAMETER; - /* Must have a valid table descriptor and pointer */ + ACPI_FUNCTION_TRACE(tb_release_owner_id); - if ((!table_desc) || (!table_desc->pointer)) { - return; + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + if (table_index < acpi_gbl_root_table_list.count) { + acpi_ut_release_owner_id(& + (acpi_gbl_root_table_list. + tables[table_index].owner_id)); + status = AE_OK; } - /* Valid table, determine type of memory allocation */ - - switch (table_desc->allocation) { - case ACPI_MEM_NOT_ALLOCATED: - break; - - case ACPI_MEM_ALLOCATED: - - ACPI_FREE(table_desc->pointer); - break; - - case ACPI_MEM_MAPPED: - - acpi_os_unmap_memory(table_desc->pointer, table_desc->length); - break; - - default: - break; - } + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + return_ACPI_STATUS(status); } /******************************************************************************* * - * FUNCTION: acpi_tb_uninstall_table + * FUNCTION: acpi_tb_get_owner_id * - * PARAMETERS: table_info - A table info struct + * PARAMETERS: table_index - Table index + * owner_id - Where the table owner_id is returned * - * RETURN: Pointer to the next table in the list (of same type) + * RETURN: Status * - * DESCRIPTION: Free the memory associated with an internal ACPI table that - * is either installed or has never been installed. - * Table mutex should be locked. + * DESCRIPTION: returns owner_id for the ACPI table * ******************************************************************************/ -struct acpi_table_desc *acpi_tb_uninstall_table(struct acpi_table_desc - *table_desc) +acpi_status +acpi_tb_get_owner_id(acpi_native_uint table_index, acpi_owner_id * owner_id) { - struct acpi_table_desc *next_desc; + acpi_status status = AE_BAD_PARAMETER; - ACPI_FUNCTION_TRACE_PTR(tb_uninstall_table, table_desc); + ACPI_FUNCTION_TRACE(tb_get_owner_id); - if (!table_desc) { - return_PTR(NULL); + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + if (table_index < acpi_gbl_root_table_list.count) { + *owner_id = + acpi_gbl_root_table_list.tables[table_index].owner_id; + status = AE_OK; } - /* Unlink the descriptor from the doubly linked list */ + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + return_ACPI_STATUS(status); +} - if (table_desc->prev) { - table_desc->prev->next = table_desc->next; - } else { - /* Is first on list, update list head */ +/******************************************************************************* + * + * FUNCTION: acpi_tb_is_table_loaded + * + * PARAMETERS: table_index - Table index + * + * RETURN: Table Loaded Flag + * + ******************************************************************************/ - acpi_gbl_table_lists[table_desc->type].next = table_desc->next; - } +u8 acpi_tb_is_table_loaded(acpi_native_uint table_index) +{ + u8 is_loaded = FALSE; - if (table_desc->next) { - table_desc->next->prev = table_desc->prev; + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + if (table_index < acpi_gbl_root_table_list.count) { + is_loaded = (u8) + (acpi_gbl_root_table_list.tables[table_index]. + flags & ACPI_TABLE_FLAGS_LOADED); } - /* Free the memory allocated for the table itself */ - - acpi_tb_delete_single_table(table_desc); - - /* Free the owner ID associated with this table */ - - acpi_ut_release_owner_id(&table_desc->owner_id); + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + return (is_loaded); +} - /* Free the table descriptor */ +/******************************************************************************* + * + * FUNCTION: acpi_tb_set_table_loaded_flag + * + * PARAMETERS: table_index - Table index + * is_loaded - TRUE if table is loaded, FALSE otherwise + * + * RETURN: None + * + * DESCRIPTION: Sets the table loaded flag to either TRUE or FALSE. + * + ******************************************************************************/ - next_desc = table_desc->next; - ACPI_FREE(table_desc); +void acpi_tb_set_table_loaded_flag(acpi_native_uint table_index, u8 is_loaded) +{ - /* Return pointer to the next descriptor */ + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + if (table_index < acpi_gbl_root_table_list.count) { + if (is_loaded) { + acpi_gbl_root_table_list.tables[table_index].flags |= + ACPI_TABLE_FLAGS_LOADED; + } else { + acpi_gbl_root_table_list.tables[table_index].flags &= + ~ACPI_TABLE_FLAGS_LOADED; + } + } - return_PTR(next_desc); + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); } diff --git a/drivers/acpi/tables/tbrsdt.c b/drivers/acpi/tables/tbrsdt.c deleted file mode 100644 index 86a5fca..0000000 --- a/drivers/acpi/tables/tbrsdt.c +++ /dev/null @@ -1,307 +0,0 @@ -/****************************************************************************** - * - * Module Name: tbrsdt - ACPI RSDT table utilities - * - *****************************************************************************/ - -/* - * Copyright (C) 2000 - 2006, R. Byron Moore - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions, and the following disclaimer, - * without modification. - * 2. Redistributions in binary form must reproduce at minimum a disclaimer - * substantially similar to the "NO WARRANTY" disclaimer below - * ("Disclaimer") and any redistribution must be conditioned upon - * including a substantially similar Disclaimer requirement for further - * binary redistribution. - * 3. Neither the names of the above-listed copyright holders nor the names - * of any contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * Alternatively, this software may be distributed under the terms of the - * GNU General Public License ("GPL") version 2 as published by the Free - * Software Foundation. - * - * NO WARRANTY - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING - * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGES. - */ - -#include -#include - -#define _COMPONENT ACPI_TABLES -ACPI_MODULE_NAME("tbrsdt") - -/******************************************************************************* - * - * FUNCTION: acpi_tb_verify_rsdp - * - * PARAMETERS: Address - RSDP (Pointer to RSDT) - * - * RETURN: Status - * - * DESCRIPTION: Load and validate the RSDP (ptr) and RSDT (table) - * - ******************************************************************************/ -acpi_status acpi_tb_verify_rsdp(struct acpi_pointer *address) -{ - struct acpi_table_desc table_info; - acpi_status status; - struct rsdp_descriptor *rsdp; - - ACPI_FUNCTION_TRACE(tb_verify_rsdp); - - switch (address->pointer_type) { - case ACPI_LOGICAL_POINTER: - - rsdp = address->pointer.logical; - break; - - case ACPI_PHYSICAL_POINTER: - /* - * Obtain access to the RSDP structure - */ - status = acpi_os_map_memory(address->pointer.physical, - sizeof(struct rsdp_descriptor), - ACPI_CAST_PTR(void, &rsdp)); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - break; - - default: - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - /* Verify RSDP signature and checksum */ - - status = acpi_tb_validate_rsdp(rsdp); - if (ACPI_FAILURE(status)) { - goto cleanup; - } - - /* RSDP is ok. Init the table info */ - - table_info.pointer = ACPI_CAST_PTR(struct acpi_table_header, rsdp); - table_info.length = sizeof(struct rsdp_descriptor); - - if (address->pointer_type == ACPI_PHYSICAL_POINTER) { - table_info.allocation = ACPI_MEM_MAPPED; - } else { - table_info.allocation = ACPI_MEM_NOT_ALLOCATED; - } - - /* Save the table pointers and allocation info */ - - status = acpi_tb_init_table_descriptor(ACPI_TABLE_ID_RSDP, &table_info); - if (ACPI_FAILURE(status)) { - goto cleanup; - } - - /* Save the RSDP in a global for easy access */ - - acpi_gbl_RSDP = - ACPI_CAST_PTR(struct rsdp_descriptor, table_info.pointer); - return_ACPI_STATUS(status); - - /* Error exit */ - cleanup: - - if (acpi_gbl_table_flags & ACPI_PHYSICAL_POINTER) { - acpi_os_unmap_memory(rsdp, sizeof(struct rsdp_descriptor)); - } - return_ACPI_STATUS(status); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_rsdt_address - * - * PARAMETERS: out_address - Where the address is returned - * - * RETURN: None, Address - * - * DESCRIPTION: Extract the address of either the RSDT or XSDT, depending on the - * version of the RSDP and whether the XSDT pointer is valid - * - ******************************************************************************/ - -void acpi_tb_get_rsdt_address(struct acpi_pointer *out_address) -{ - - ACPI_FUNCTION_ENTRY(); - - out_address->pointer_type = - acpi_gbl_table_flags | ACPI_LOGICAL_ADDRESSING; - - /* Use XSDT if it is present */ - - if ((acpi_gbl_RSDP->revision >= 2) && - acpi_gbl_RSDP->xsdt_physical_address) { - out_address->pointer.value = - acpi_gbl_RSDP->xsdt_physical_address; - acpi_gbl_root_table_type = ACPI_TABLE_TYPE_XSDT; - } else { - /* No XSDT, use the RSDT */ - - out_address->pointer.value = - acpi_gbl_RSDP->rsdt_physical_address; - acpi_gbl_root_table_type = ACPI_TABLE_TYPE_RSDT; - } -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_validate_rsdt - * - * PARAMETERS: table_ptr - Addressable pointer to the RSDT. - * - * RETURN: Status - * - * DESCRIPTION: Validate signature for the RSDT or XSDT - * - ******************************************************************************/ - -acpi_status acpi_tb_validate_rsdt(struct acpi_table_header *table_ptr) -{ - char *signature; - - ACPI_FUNCTION_ENTRY(); - - /* Validate minimum length */ - - if (table_ptr->length < sizeof(struct acpi_table_header)) { - ACPI_ERROR((AE_INFO, - "RSDT/XSDT length (%X) is smaller than minimum (%zX)", - table_ptr->length, - sizeof(struct acpi_table_header))); - - return (AE_INVALID_TABLE_LENGTH); - } - - /* Search for appropriate signature, RSDT or XSDT */ - - if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { - signature = RSDT_SIG; - } else { - signature = XSDT_SIG; - } - - if (!ACPI_COMPARE_NAME(table_ptr->signature, signature)) { - - /* Invalid RSDT or XSDT signature */ - - ACPI_ERROR((AE_INFO, - "Invalid signature where RSDP indicates RSDT/XSDT should be located. RSDP:")); - - ACPI_DUMP_BUFFER(acpi_gbl_RSDP, 20); - - ACPI_ERROR((AE_INFO, - "RSDT/XSDT signature at %X is invalid", - acpi_gbl_RSDP->rsdt_physical_address)); - - if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { - ACPI_ERROR((AE_INFO, "Looking for RSDT")); - } else { - ACPI_ERROR((AE_INFO, "Looking for XSDT")); - } - - ACPI_DUMP_BUFFER(ACPI_CAST_PTR(char, table_ptr), 48); - return (AE_BAD_SIGNATURE); - } - - return (AE_OK); -} - -/******************************************************************************* - * - * FUNCTION: acpi_tb_get_table_rsdt - * - * PARAMETERS: None - * - * RETURN: Status - * - * DESCRIPTION: Load and validate the RSDP (ptr) and RSDT (table) - * - ******************************************************************************/ - -acpi_status acpi_tb_get_table_rsdt(void) -{ - struct acpi_table_desc table_info; - acpi_status status; - struct acpi_pointer address; - - ACPI_FUNCTION_TRACE(tb_get_table_rsdt); - - /* Get the RSDT/XSDT via the RSDP */ - - acpi_tb_get_rsdt_address(&address); - - table_info.type = ACPI_TABLE_ID_XSDT; - status = acpi_tb_get_table(&address, &table_info); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "Could not get the RSDT/XSDT")); - return_ACPI_STATUS(status); - } - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "RSDP located at %p, points to RSDT physical=%8.8X%8.8X\n", - acpi_gbl_RSDP, - ACPI_FORMAT_UINT64(address.pointer.value))); - - /* Check the RSDT or XSDT signature */ - - status = acpi_tb_validate_rsdt(table_info.pointer); - if (ACPI_FAILURE(status)) { - goto error_cleanup; - } - - /* Get the number of tables defined in the RSDT or XSDT */ - - acpi_gbl_rsdt_table_count = acpi_tb_get_table_count(acpi_gbl_RSDP, - table_info.pointer); - - /* Convert and/or copy to an XSDT structure */ - - status = acpi_tb_convert_to_xsdt(&table_info); - if (ACPI_FAILURE(status)) { - goto error_cleanup; - } - - /* Save the table pointers and allocation info */ - - status = acpi_tb_init_table_descriptor(ACPI_TABLE_ID_XSDT, &table_info); - if (ACPI_FAILURE(status)) { - goto error_cleanup; - } - - acpi_gbl_XSDT = - ACPI_CAST_PTR(struct xsdt_descriptor, table_info.pointer); - - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "XSDT located at %p\n", acpi_gbl_XSDT)); - return_ACPI_STATUS(status); - - error_cleanup: - - /* Free table allocated by acpi_tb_get_table */ - - acpi_tb_delete_single_table(&table_info); - - return_ACPI_STATUS(status); -} diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 209a401..3620ac5 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -1,6 +1,6 @@ /****************************************************************************** * - * Module Name: tbutils - Table manipulation utilities + * Module Name: tbutils - table utilities * *****************************************************************************/ @@ -48,295 +48,507 @@ ACPI_MODULE_NAME("tbutils") /* Local prototypes */ -#ifdef ACPI_OBSOLETE_FUNCTIONS -acpi_status -acpi_tb_handle_to_object(u16 table_id, struct acpi_table_desc **table_desc); -#endif +static void acpi_tb_parse_fadt(struct acpi_table_fadt *fadt, u8 flags); + +static void inline +acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, + u8 bit_width, acpi_physical_address address); /******************************************************************************* * - * FUNCTION: acpi_tb_is_table_installed + * FUNCTION: acpi_tb_print_table_header * - * PARAMETERS: new_table_desc - Descriptor for new table being installed + * PARAMETERS: Address - Table physical address + * Header - Table header * - * RETURN: Status - AE_ALREADY_EXISTS if the table is already installed + * RETURN: None * - * DESCRIPTION: Determine if an ACPI table is already installed - * - * MUTEX: Table data structures should be locked + * DESCRIPTION: Print an ACPI table header * ******************************************************************************/ -acpi_status acpi_tb_is_table_installed(struct acpi_table_desc *new_table_desc) +void +acpi_tb_print_table_header(acpi_physical_address address, + struct acpi_table_header *header) { - struct acpi_table_desc *table_desc; - - ACPI_FUNCTION_TRACE(tb_is_table_installed); - - /* Get the list descriptor and first table descriptor */ - - table_desc = acpi_gbl_table_lists[new_table_desc->type].next; - - /* Examine all installed tables of this type */ - - while (table_desc) { - /* - * If the table lengths match, perform a full bytewise compare. This - * means that we will allow tables with duplicate oem_table_id(s), as - * long as the tables are different in some way. - * - * Checking if the table has been loaded into the namespace means that - * we don't check for duplicate tables during the initial installation - * of tables within the RSDT/XSDT. - */ - if ((table_desc->loaded_into_namespace) && - (table_desc->pointer->length == - new_table_desc->pointer->length) - && - (!ACPI_MEMCMP - (table_desc->pointer, new_table_desc->pointer, - new_table_desc->pointer->length))) { - - /* Match: this table is already installed */ - - ACPI_DEBUG_PRINT((ACPI_DB_TABLES, - "Table [%4.4s] already installed: Rev %X OemTableId [%8.8s]\n", - new_table_desc->pointer->signature, - new_table_desc->pointer->revision, - new_table_desc->pointer-> - oem_table_id)); - - new_table_desc->owner_id = table_desc->owner_id; - new_table_desc->installed_desc = table_desc; - - return_ACPI_STATUS(AE_ALREADY_EXISTS); - } - - /* Get next table on the list */ - table_desc = table_desc->next; - } - - return_ACPI_STATUS(AE_OK); + ACPI_INFO((AE_INFO, + "%4.4s @ 0x%p Length 0x%04X (v%3.3d %6.6s %8.8s 0x%08X %4.4s 0x%08X)", + header->signature, ACPI_CAST_PTR(void, address), + header->length, header->revision, header->oem_id, + header->oem_table_id, header->oem_revision, + header->asl_compiler_id, header->asl_compiler_revision)); } /******************************************************************************* * - * FUNCTION: acpi_tb_validate_table_header - * - * PARAMETERS: table_header - Logical pointer to the table + * FUNCTION: acpi_tb_init_generic_address * - * RETURN: Status + * PARAMETERS: new_gas_struct - GAS struct to be initialized + * bit_width - Width of this register + * Address - Address of the register * - * DESCRIPTION: Check an ACPI table header for validity + * RETURN: None * - * NOTE: Table pointers are validated as follows: - * 1) Table pointer must point to valid physical memory - * 2) Signature must be 4 ASCII chars, even if we don't recognize the - * name - * 3) Table must be readable for length specified in the header - * 4) Table checksum must be valid (with the exception of the FACS - * which has no checksum because it contains variable fields) + * DESCRIPTION: Initialize a GAS structure. * ******************************************************************************/ -acpi_status -acpi_tb_validate_table_header(struct acpi_table_header *table_header) +static void inline +acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, + u8 bit_width, acpi_physical_address address) { - acpi_name signature; - - ACPI_FUNCTION_ENTRY(); - - /* Verify that this is a valid address */ - - if (!acpi_os_readable(table_header, sizeof(struct acpi_table_header))) { - ACPI_ERROR((AE_INFO, - "Cannot read table header at %p", table_header)); - - return (AE_BAD_ADDRESS); - } - - /* Ensure that the signature is 4 ASCII characters */ - - ACPI_MOVE_32_TO_32(&signature, table_header->signature); - if (!acpi_ut_valid_acpi_name(signature)) { - ACPI_ERROR((AE_INFO, "Invalid table signature 0x%8.8X", - signature)); - ACPI_DUMP_BUFFER(table_header, - sizeof(struct acpi_table_header)); - return (AE_BAD_SIGNATURE); - } - - /* Validate the table length */ - - if (table_header->length < sizeof(struct acpi_table_header)) { - ACPI_ERROR((AE_INFO, - "Invalid length 0x%X in table with signature %4.4s", - (u32) table_header->length, - ACPI_CAST_PTR(char, &signature))); - - ACPI_DUMP_BUFFER(table_header, - sizeof(struct acpi_table_header)); - return (AE_BAD_HEADER); - } - - return (AE_OK); + ACPI_STORE_ADDRESS(new_gas_struct->address, address); + new_gas_struct->space_id = ACPI_ADR_SPACE_SYSTEM_IO; + new_gas_struct->bit_width = bit_width; + new_gas_struct->bit_offset = 0; + new_gas_struct->access_width = 0; } /******************************************************************************* * - * FUNCTION: acpi_tb_sum_table + * FUNCTION: acpi_tb_checksum * - * PARAMETERS: Buffer - Buffer to sum - * Length - Size of the buffer + * PARAMETERS: Buffer - Pointer to memory region to be checked + * Length - Length of this memory region * - * RETURN: 8 bit sum of buffer + * RETURN: Checksum (u8) * - * DESCRIPTION: Computes an 8 bit sum of the buffer(length) and returns it. + * DESCRIPTION: Calculates circular checksum of memory region. * ******************************************************************************/ -u8 acpi_tb_sum_table(void *buffer, u32 length) +u8 acpi_tb_checksum(u8 * buffer, acpi_native_uint length) { - acpi_native_uint i; u8 sum = 0; + u8 *end = buffer + length; - if (!buffer || !length) { - return (0); + while (buffer < end) { + sum = (u8) (sum + *(buffer++)); } - for (i = 0; i < length; i++) { - sum = (u8) (sum + ((u8 *) buffer)[i]); - } - return (sum); + return sum; } /******************************************************************************* * - * FUNCTION: acpi_tb_generate_checksum + * FUNCTION: acpi_tb_convert_fadt * - * PARAMETERS: Table - Pointer to a valid ACPI table (with a - * standard ACPI header) + * PARAMETERS: Fadt - FADT table to be converted * - * RETURN: 8 bit checksum of buffer + * RETURN: None * - * DESCRIPTION: Computes an 8 bit checksum of the table. + * DESCRIPTION: Converts a BIOS supplied ACPI 1.0 FADT to a local + * ACPI 2.0 FADT. If the BIOS supplied a 2.0 FADT then it is simply + * copied to the local FADT. The ACPI CA software uses this + * local FADT. Thus a significant amount of special #ifdef + * type codeing is saved. * ******************************************************************************/ -u8 acpi_tb_generate_checksum(struct acpi_table_header * table) +void acpi_tb_convert_fadt(struct acpi_table_fadt *fadt) { - u8 checksum; - - /* Sum the entire table as-is */ - checksum = acpi_tb_sum_table(table, table->length); + /* + * Convert table pointers to 64-bit fields + */ + if (!acpi_gbl_FADT.Xfacs) { + acpi_gbl_FADT.Xfacs = (u64) acpi_gbl_FADT.facs; + } - /* Subtract off the existing checksum value in the table */ + if (!acpi_gbl_FADT.Xdsdt) { + acpi_gbl_FADT.Xdsdt = (u64) acpi_gbl_FADT.dsdt; + } - checksum = (u8) (checksum - table->checksum); + /* + * Convert the V1.0 block addresses to V2.0 GAS structures + */ + acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1a_event_block, + acpi_gbl_FADT.pm1_event_length, + (acpi_physical_address) acpi_gbl_FADT. + pm1a_event_block); + acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1b_event_block, + acpi_gbl_FADT.pm1_event_length, + (acpi_physical_address) acpi_gbl_FADT. + pm1b_event_block); + acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1a_control_block, + acpi_gbl_FADT.pm1_control_length, + (acpi_physical_address) acpi_gbl_FADT. + pm1a_control_block); + acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1b_control_block, + acpi_gbl_FADT.pm1_control_length, + (acpi_physical_address) acpi_gbl_FADT. + pm1b_control_block); + acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm2_control_block, + acpi_gbl_FADT.pm2_control_length, + (acpi_physical_address) acpi_gbl_FADT. + pm2_control_block); + acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm_timer_block, + acpi_gbl_FADT.pm_timer_length, + (acpi_physical_address) acpi_gbl_FADT. + pm_timer_block); + acpi_tb_init_generic_address(&acpi_gbl_FADT.xgpe0_block, 0, + (acpi_physical_address) acpi_gbl_FADT. + gpe0_block); + acpi_tb_init_generic_address(&acpi_gbl_FADT.xgpe1_block, 0, + (acpi_physical_address) acpi_gbl_FADT. + gpe1_block); + + /* + * Create separate GAS structs for the PM1 Enable registers + */ + acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, + (u8) ACPI_DIV_2(acpi_gbl_FADT. + pm1_event_length), + (acpi_physical_address) + (acpi_gbl_FADT.xpm1a_event_block.address + + ACPI_DIV_2(acpi_gbl_FADT. + pm1_event_length))); + + /* + * PM1B is optional; leave null if not present + */ + if (acpi_gbl_FADT.xpm1b_event_block.address) { + acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, + (u8) ACPI_DIV_2(acpi_gbl_FADT. + pm1_event_length), + (acpi_physical_address) + (acpi_gbl_FADT.xpm1b_event_block. + address + + ACPI_DIV_2(acpi_gbl_FADT. + pm1_event_length))); + } - /* Compute the final checksum */ + /* Global FADT is the new common V2.0 FADT */ - checksum = (u8) (0 - checksum); - return (checksum); + acpi_gbl_FADT.header.length = sizeof(struct acpi_table_fadt); } /******************************************************************************* * - * FUNCTION: acpi_tb_set_checksum + * FUNCTION: acpi_tb_parse_fadt * - * PARAMETERS: Table - Pointer to a valid ACPI table (with a - * standard ACPI header) + * PARAMETERS: Fadt - Pointer to FADT table + * Flags - Flags * - * RETURN: None. Sets the table checksum field + * RETURN: none * - * DESCRIPTION: Computes an 8 bit checksum of the table and inserts the - * checksum into the table header. + * DESCRIPTION: This function is called to initialise the FADT, DSDT and FACS + * tables (FADT contains the addresses of the DSDT and FACS) * ******************************************************************************/ -void acpi_tb_set_checksum(struct acpi_table_header *table) +static void acpi_tb_parse_fadt(struct acpi_table_fadt *fadt, u8 flags) { + acpi_physical_address dsdt_address = + (acpi_physical_address) fadt->Xdsdt; + acpi_physical_address facs_address = + (acpi_physical_address) fadt->Xfacs; + struct acpi_table_header *table; + + if (!dsdt_address) { + goto no_dsdt; + } + + table = + acpi_os_map_memory(dsdt_address, sizeof(struct acpi_table_header)); + if (!table) { + goto no_dsdt; + } + + /* Initialize the DSDT table */ + + ACPI_MOVE_32_TO_32(& + (acpi_gbl_root_table_list. + tables[ACPI_TABLE_INDEX_DSDT].signature), + ACPI_SIG_DSDT); + + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].address = + dsdt_address; + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].length = + table->length; + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].flags = flags; + + acpi_tb_print_table_header(dsdt_address, table); + + /* Global integer width is based upon revision of the DSDT */ + + acpi_ut_set_integer_width(table->revision); + acpi_os_unmap_memory(table, sizeof(struct acpi_table_header)); + + no_dsdt: + if (!facs_address) { + return; + } - table->checksum = acpi_tb_generate_checksum(table); + table = + acpi_os_map_memory(facs_address, sizeof(struct acpi_table_header)); + if (!table) { + return; + } + + /* Initialize the FACS table */ + + ACPI_MOVE_32_TO_32(& + (acpi_gbl_root_table_list. + tables[ACPI_TABLE_INDEX_FACS].signature), + ACPI_SIG_FACS); + + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_FACS].address = + facs_address; + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_FACS].length = + table->length; + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_FACS].flags = flags; + + ACPI_INFO((AE_INFO, "%4.4s @ 0x%p", + table->signature, ACPI_CAST_PTR(void, facs_address))); + + acpi_os_unmap_memory(table, sizeof(struct acpi_table_header)); } /******************************************************************************* * - * FUNCTION: acpi_tb_verify_table_checksum + * FUNCTION: acpi_tb_parse_root_table * - * PARAMETERS: *table_header - ACPI table to verify + * PARAMETERS: Rsdp - Pointer to the RSDP + * Flags - Flags + * + * RETURN: Status * - * RETURN: 8 bit checksum of table + * DESCRIPTION: This function is called to parse the Root System Description + * Table (RSDT or XSDT) * - * DESCRIPTION: Generates an 8 bit checksum of table and returns and compares - * it to the existing checksum value. + * NOTE: Tables are mapped (not copied) for efficiency. The FACS must + * be mapped and cannot be copied because it contains the actual + * memory location of the ACPI Global Lock. * ******************************************************************************/ -acpi_status -acpi_tb_verify_table_checksum(struct acpi_table_header *table_header) +acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags) { + struct acpi_table_header *table; + acpi_physical_address address; + u32 length; + u8 *table_entry; + acpi_native_uint i; + acpi_native_uint pointer_size; + u32 table_count; u8 checksum; + acpi_status status; + + ACPI_FUNCTION_TRACE(tb_parse_root_table); + + /* Differentiate between RSDT and XSDT root tables */ + + if (rsdp->revision > 1 && rsdp->xsdt_physical_address) { + /* + * Root table is an XSDT (64-bit physical addresses). We must use the + * XSDT if the revision is > 1 and the XSDT pointer is present, as per + * the ACPI specification. + */ + address = (acpi_native_uint) rsdp->xsdt_physical_address; + pointer_size = sizeof(u64); + } else { + /* Root table is an RSDT (32-bit physical addresses) */ + + address = (acpi_native_uint) rsdp->rsdt_physical_address; + pointer_size = sizeof(u32); + } - ACPI_FUNCTION_TRACE(tb_verify_table_checksum); + /* Map the table header to get the full table length */ - /* Compute the checksum on the table */ + table = acpi_os_map_memory(address, sizeof(struct acpi_table_header)); + if (!table) { + return (AE_NO_MEMORY); + } + + /* Get the length of the full table, verify length and map entire table */ + + length = table->length; + acpi_os_unmap_memory(table, sizeof(struct acpi_table_header)); + + if (length < sizeof(struct acpi_table_header)) { + ACPI_ERROR((AE_INFO, "Invalid length 0x%X in RSDT/XSDT", + length)); + return (AE_INVALID_TABLE_LENGTH); + } + + table = acpi_os_map_memory(address, length); + if (!table) { + return (AE_NO_MEMORY); + } + + /* Validate the root table checksum */ + + checksum = acpi_tb_checksum(ACPI_CAST_PTR(u8, table), length); +#if (ACPI_CHECKSUM_ABORT) + + if (checksum) { + acpi_os_unmap_memory(table, length); + return (AE_BAD_CHECKSUM); + } +#endif + + acpi_tb_print_table_header(address, table); + + /* Calculate the number of tables described in the root table */ + + table_count = + (table->length - sizeof(struct acpi_table_header)) / pointer_size; + + /* Setup loop */ - checksum = acpi_tb_generate_checksum(table_header); + table_entry = + ACPI_CAST_PTR(u8, table) + sizeof(struct acpi_table_header); + acpi_gbl_root_table_list.count = 2; - /* Checksum ok? */ + /* + * Initialize the ACPI table entries + * First two entries in the table array are reserved for the DSDT and FACS + */ + for (i = 0; i < table_count; ++i, table_entry += pointer_size) { - if (checksum == table_header->checksum) { - return_ACPI_STATUS(AE_OK); + /* Ensure there is room for another table entry */ + + if (acpi_gbl_root_table_list.count >= + acpi_gbl_root_table_list.size) { + status = acpi_tb_resize_root_table_list(); + if (ACPI_FAILURE(status)) { + ACPI_WARNING((AE_INFO, + "Truncating %u table entries!", + (unsigned) + (acpi_gbl_root_table_list.size - + acpi_gbl_root_table_list. + count))); + break; + } + } + + /* Get the physical address (32-bit for RSDT, 64-bit for XSDT) */ + + if (pointer_size == sizeof(u32)) { + acpi_gbl_root_table_list. + tables[acpi_gbl_root_table_list.count].address = + (acpi_physical_address) (*ACPI_CAST_PTR + (u32, table_entry)); + } else { + acpi_gbl_root_table_list. + tables[acpi_gbl_root_table_list.count].address = + (acpi_physical_address) (*ACPI_CAST_PTR + (u64, table_entry)); + } + + acpi_gbl_root_table_list.count++; } - ACPI_WARNING((AE_INFO, - "Incorrect checksum in table [%4.4s] - is %2.2X, should be %2.2X", - table_header->signature, table_header->checksum, - checksum)); + /* + * It is not possible to map more than one entry in some environments, + * so unmap the root table here before mapping other tables + */ + acpi_os_unmap_memory(table, length); + + /* Initialize all tables other than the DSDT and FACS */ + + for (i = 2; i < acpi_gbl_root_table_list.count; i++) { + address = acpi_gbl_root_table_list.tables[i].address; + length = sizeof(struct acpi_table_header); + + table = acpi_os_map_memory(address, length); + if (!table) { + continue; + } + + acpi_gbl_root_table_list.tables[i].length = table->length; + acpi_gbl_root_table_list.tables[i].flags = flags; + + ACPI_MOVE_32_TO_32(& + (acpi_gbl_root_table_list.tables[i]. + signature), table->signature); + + acpi_tb_print_table_header(address, table); + + /* + * Special case for the FADT because of multiple versions - + * get a local copy and convert to common format + */ + if (ACPI_COMPARE_NAME(table->signature, ACPI_SIG_FADT)) { + acpi_os_unmap_memory(table, length); + length = table->length; + + table = acpi_os_map_memory(address, length); + if (!table) { + continue; + } + + /* Copy the entire FADT locally */ + + ACPI_MEMCPY(&acpi_gbl_FADT, table, + ACPI_MIN(table->length, + sizeof(struct acpi_table_fadt))); + + /* Small table means old revision, convert to new */ + + if (table->length < sizeof(struct acpi_table_fadt)) { + acpi_tb_convert_fadt(ACPI_CAST_PTR + (struct acpi_table_fadt, + table)); + } + + /* Unmap original FADT */ - return_ACPI_STATUS(AE_BAD_CHECKSUM); + acpi_os_unmap_memory(table, length); + acpi_tb_parse_fadt(&acpi_gbl_FADT, flags); + } else { + acpi_os_unmap_memory(table, length); + } + } + + return_ACPI_STATUS(AE_OK); } -#ifdef ACPI_OBSOLETE_FUNCTIONS -/******************************************************************************* +/****************************************************************************** * - * FUNCTION: acpi_tb_handle_to_object + * FUNCTION: acpi_tb_map * - * PARAMETERS: table_id - Id for which the function is searching - * table_desc - Pointer to return the matching table - * descriptor. + * PARAMETERS: Address - Address to be mapped + * Length - Length to be mapped + * Flags - Logical or physical addressing mode * - * RETURN: Search the tables to find one with a matching table_id and - * return a pointer to that table descriptor. + * RETURN: Pointer to mapped region * - ******************************************************************************/ + * DESCRIPTION: Maps memory according to flag + * + *****************************************************************************/ -acpi_status -acpi_tb_handle_to_object(u16 table_id, - struct acpi_table_desc **return_table_desc) +void *acpi_tb_map(acpi_physical_address address, u32 length, u32 flags) { - u32 i; - struct acpi_table_desc *table_desc; - ACPI_FUNCTION_NAME(tb_handle_to_object); + if (flags == ACPI_TABLE_ORIGIN_MAPPED) { + return (acpi_os_map_memory(address, length)); + } else { + return (ACPI_CAST_PTR(void, address)); + } +} - for (i = 0; i < ACPI_TABLE_MAX; i++) { - table_desc = acpi_gbl_table_lists[i].next; - while (table_desc) { - if (table_desc->table_id == table_id) { - *return_table_desc = table_desc; - return (AE_OK); - } +/****************************************************************************** + * + * FUNCTION: acpi_tb_unmap + * + * PARAMETERS: Pointer - To mapped region + * Length - Length to be unmapped + * Flags - Logical or physical addressing mode + * + * RETURN: None + * + * DESCRIPTION: Unmaps memory according to flag + * + *****************************************************************************/ - table_desc = table_desc->next; - } - } +void acpi_tb_unmap(void *pointer, u32 length, u32 flags) +{ - ACPI_ERROR((AE_INFO, "TableId=%X does not exist", table_id)); - return (AE_BAD_PARAMETER); + if (flags == ACPI_TABLE_ORIGIN_MAPPED) { + acpi_os_unmap_memory(pointer, length); + } } -#endif diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 5ba9303..77439fc 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -49,80 +49,146 @@ #define _COMPONENT ACPI_TABLES ACPI_MODULE_NAME("tbxface") +/* Local prototypes */ +static acpi_status acpi_tb_load_namespace(void); + /******************************************************************************* * - * FUNCTION: acpi_load_tables + * FUNCTION: acpi_initialize_tables * - * PARAMETERS: None + * PARAMETERS: initial_table_array - Pointer to an array of pre-allocated + * struct acpi_table_desc structures. If NULL, the + * array is dynamically allocated. + * initial_table_count - Size of initial_table_array, in number of + * struct acpi_table_desc structures + * allow_realloc - Flag to tell Table Manager if resize of + * pre-allocated array is allowed. Ignored + * if initial_table_array is NULL. * * RETURN: Status * - * DESCRIPTION: This function is called to load the ACPI tables from the - * provided RSDT + * DESCRIPTION: Initialize the table manager, get the RSDP and RSDT/XSDT. + * + * NOTE: Allows static allocation of the initial table array in order + * to avoid the use of dynamic memory in confined environments + * such as the kernel boot sequence where it may not be available. + * + * If the host OS memory managers are initialized, use NULL for + * initial_table_array, and the table will be dynamically allocated. * ******************************************************************************/ -acpi_status acpi_load_tables(void) + +acpi_status +acpi_initialize_tables(struct acpi_table_desc *initial_table_array, + u32 initial_table_count, u8 allow_resize) { - struct acpi_pointer rsdp_address; + acpi_physical_address address; acpi_status status; + struct acpi_table_rsdp *rsdp; - ACPI_FUNCTION_TRACE(acpi_load_tables); + ACPI_FUNCTION_TRACE(acpi_initialize_tables); - /* Get the RSDP */ + /* + * Set up the Root Table Array + * Allocate the table array if requested + */ + if (!initial_table_array) { + acpi_gbl_root_table_list.size = initial_table_count; + acpi_gbl_root_table_list.flags = ACPI_TABLE_FLAGS_ALLOW_RESIZE; - status = acpi_os_get_root_pointer(ACPI_LOGICAL_ADDRESSING, - &rsdp_address); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, "Could not get the RSDP")); - goto error_exit; + status = acpi_tb_resize_root_table_list(); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + } else { + /* Root Table Array has been statically allocated by the host */ + + acpi_gbl_root_table_list.tables = initial_table_array; + acpi_gbl_root_table_list.size = initial_table_count; + acpi_gbl_root_table_list.flags = ACPI_TABLE_ORIGIN_UNKNOWN; + if (allow_resize) { + acpi_gbl_root_table_list.flags = + ACPI_TABLE_FLAGS_ALLOW_RESIZE; + } } - /* Map and validate the RSDP */ + /* Get the RSDP and map it */ - acpi_gbl_table_flags = rsdp_address.pointer_type; + address = acpi_os_get_root_pointer(); + if (!address) { + return_ACPI_STATUS(AE_NOT_FOUND); + } - status = acpi_tb_verify_rsdp(&rsdp_address); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, "During RSDP validation")); - goto error_exit; + rsdp = acpi_os_map_memory(address, sizeof(struct acpi_table_rsdp)); + if (!rsdp) { + return_ACPI_STATUS(AE_NO_MEMORY); } - /* Get the RSDT via the RSDP */ + ACPI_INFO((AE_INFO, "%.8s @ 0x%p", + rsdp->signature, ACPI_CAST_PTR(void, address))); - status = acpi_tb_get_table_rsdt(); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, "Could not load RSDT")); - goto error_exit; - } + /* + * Get the root table (RSDT or XSDT) and extract all entries to the local + * Root Table Array. This array contains the information of the RSDT/XSDT + * in a common, more useable format. + */ + status = acpi_tb_parse_root_table(rsdp, ACPI_TABLE_ORIGIN_MAPPED); + acpi_os_unmap_memory(rsdp, sizeof(struct acpi_table_rsdp)); + return_ACPI_STATUS(status); +} - /* Now get the tables needed by this subsystem (FADT, DSDT, etc.) */ +ACPI_EXPORT_SYMBOL(acpi_initialize_tables) - status = acpi_tb_get_required_tables(); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "Could not get all required tables (DSDT/FADT/FACS)")); - goto error_exit; +/******************************************************************************* + * + * FUNCTION: acpi_reallocate_root_table + * + * PARAMETERS: None + * + * RETURN: Status + * + * DESCRIPTION: Reallocate Root Table List into dynamic memory. Copies the + * root list from the previously provided scratch area. Should + * be called once dynamic memory allocation is available in the + * kernel + * + ******************************************************************************/ +acpi_status acpi_reallocate_root_table(void) +{ + struct acpi_table_desc *tables; + acpi_size new_size; + + ACPI_FUNCTION_TRACE(acpi_reallocate_root_table); + + /* + * Only reallocate the root table if the host provided a static buffer + * for the table array in the call to acpi_initialize_tables. + */ + if ((acpi_gbl_root_table_list.flags & ACPI_TABLE_ORIGIN_MASK) != + ACPI_TABLE_ORIGIN_UNKNOWN) { + return_ACPI_STATUS(AE_SUPPORT); } - ACPI_DEBUG_PRINT((ACPI_DB_INIT, "ACPI Tables successfully acquired\n")); + new_size = + (acpi_gbl_root_table_list.count + + ACPI_ROOT_TABLE_SIZE_INCREMENT) * sizeof(struct acpi_table_desc); - /* Load the namespace from the tables */ + /* Create new array and copy the old array */ - status = acpi_ns_load_namespace(); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, "Could not load namespace")); - goto error_exit; + tables = ACPI_ALLOCATE_ZEROED(new_size); + if (!tables) { + return_ACPI_STATUS(AE_NO_MEMORY); } - return_ACPI_STATUS(AE_OK); + ACPI_MEMCPY(tables, acpi_gbl_root_table_list.tables, new_size); - error_exit: - ACPI_EXCEPTION((AE_INFO, status, "Could not load tables")); - return_ACPI_STATUS(status); -} - -ACPI_EXPORT_SYMBOL(acpi_load_tables) + acpi_gbl_root_table_list.size = acpi_gbl_root_table_list.count; + acpi_gbl_root_table_list.tables = tables; + acpi_gbl_root_table_list.flags = + ACPI_TABLE_ORIGIN_ALLOCATED | ACPI_TABLE_FLAGS_ALLOW_RESIZE; + return_ACPI_STATUS(AE_OK); +} /******************************************************************************* * * FUNCTION: acpi_load_table @@ -141,342 +207,358 @@ ACPI_EXPORT_SYMBOL(acpi_load_tables) acpi_status acpi_load_table(struct acpi_table_header *table_ptr) { acpi_status status; - struct acpi_table_desc table_info; - struct acpi_pointer address; - - ACPI_FUNCTION_TRACE(acpi_load_table); - - if (!table_ptr) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } + acpi_native_uint table_index; - /* Copy the table to a local buffer */ - - address.pointer_type = ACPI_LOGICAL_POINTER | ACPI_LOGICAL_ADDRESSING; - address.pointer.logical = table_ptr; - - status = acpi_tb_get_table_body(&address, table_ptr, &table_info); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Check signature for a valid table type */ - - status = acpi_tb_recognize_table(&table_info, ACPI_TABLE_ALL); + /* + * Install the new table into the local data structures + */ + status = acpi_tb_add_table(table_ptr, &table_index); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } + status = acpi_ns_load_table(table_index, acpi_gbl_root_node); + return_ACPI_STATUS(status); +} - /* Install the new table into the local data structures */ - - status = acpi_tb_install_table(&table_info); - if (ACPI_FAILURE(status)) { - if (status == AE_ALREADY_EXISTS) { +ACPI_EXPORT_SYMBOL(acpi_load_table) - /* Table already exists, no error */ +/****************************************************************************** + * + * FUNCTION: acpi_get_table_header + * + * PARAMETERS: Signature - ACPI signature of needed table + * Instance - Which instance (for SSDTs) + * out_table_header - Where the pointer to the table header + * is returned + * + * RETURN: Status and pointer to mapped table header + * + * DESCRIPTION: Finds an ACPI table header. + * + * NOTE: Caller is responsible in unmapping the header with + * acpi_os_unmap_memory + * + *****************************************************************************/ +acpi_status +acpi_get_table_header(char *signature, + acpi_native_uint instance, + struct acpi_table_header **out_table_header) +{ + acpi_native_uint i; + acpi_native_uint j; - status = AE_OK; + /* + * Walk the root table list + */ + for (i = 0, j = 0; i < acpi_gbl_root_table_list.count; i++) { + if (!ACPI_COMPARE_NAME + (&(acpi_gbl_root_table_list.tables[i].signature), + signature)) { + continue; } - /* Free table allocated by acpi_tb_get_table_body */ - - acpi_tb_delete_single_table(&table_info); - return_ACPI_STATUS(status); - } - - /* Convert the table to common format if necessary */ - - switch (table_info.type) { - case ACPI_TABLE_ID_FADT: - - status = acpi_tb_convert_table_fadt(); - break; - - case ACPI_TABLE_ID_FACS: - - status = acpi_tb_build_common_facs(&table_info); - break; - - default: - /* Load table into namespace if it contains executable AML */ - - status = - acpi_ns_load_table(table_info.installed_desc, - acpi_gbl_root_node); - break; - } + if (++j < instance) { + continue; + } - if (ACPI_FAILURE(status)) { + *out_table_header = + acpi_tb_map(acpi_gbl_root_table_list.tables[i].address, + (u32) sizeof(struct acpi_table_header), + acpi_gbl_root_table_list.tables[i]. + flags & ACPI_TABLE_ORIGIN_MASK); - /* Uninstall table and free the buffer */ + if (!out_table_header) { + return (AE_NO_MEMORY); + } - (void)acpi_tb_uninstall_table(table_info.installed_desc); + return (AE_OK); } - return_ACPI_STATUS(status); + return (AE_NOT_FOUND); } -ACPI_EXPORT_SYMBOL(acpi_load_table) +ACPI_EXPORT_SYMBOL(acpi_get_table_header) -/******************************************************************************* + +/****************************************************************************** * * FUNCTION: acpi_unload_table_id * - * PARAMETERS: table_type - Type of table to be unloaded - * id - Owner ID of the table to be removed. + * PARAMETERS: id - Owner ID of the table to be removed. * * RETURN: Status * * DESCRIPTION: This routine is used to force the unload of a table (by id) * ******************************************************************************/ -acpi_status acpi_unload_table_id(acpi_table_type table_type, acpi_owner_id id) +acpi_status acpi_unload_table_id(acpi_owner_id id) { - struct acpi_table_desc *table_desc; - acpi_status status; + int i; + acpi_status status = AE_NOT_EXIST; ACPI_FUNCTION_TRACE(acpi_unload_table); - /* Parameter validation */ - if (table_type > ACPI_TABLE_ID_MAX) - return_ACPI_STATUS(AE_BAD_PARAMETER); - /* Find table from the requested type list */ - table_desc = acpi_gbl_table_lists[table_type].next; - while (table_desc && table_desc->owner_id != id) - table_desc = table_desc->next; - - if (!table_desc) - return_ACPI_STATUS(AE_NOT_EXIST); - - /* - * Delete all namespace objects owned by this table. Note that these - * objects can appear anywhere in the namespace by virtue of the AML - * "Scope" operator. Thus, we need to track ownership by an ID, not - * simply a position within the hierarchy - */ - acpi_ns_delete_namespace_by_owner(table_desc->owner_id); - - status = acpi_ut_acquire_mutex(ACPI_MTX_TABLES); - if (ACPI_FAILURE(status)) - return_ACPI_STATUS(status); - - (void)acpi_tb_uninstall_table(table_desc); - - (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); - - return_ACPI_STATUS(AE_OK); + for (i = 0; i < acpi_gbl_root_table_list.count; ++i) { + if (id != acpi_gbl_root_table_list.tables[i].owner_id) { + continue; + } + /* + * Delete all namespace objects owned by this table. Note that these + * objects can appear anywhere in the namespace by virtue of the AML + * "Scope" operator. Thus, we need to track ownership by an ID, not + * simply a position within the hierarchy + */ + acpi_tb_delete_namespace_by_owner(i); + acpi_tb_release_owner_id(i); + acpi_tb_set_table_loaded_flag(i, FALSE); + } + return_ACPI_STATUS(status); } ACPI_EXPORT_SYMBOL(acpi_unload_table_id) -#ifdef ACPI_FUTURE_USAGE /******************************************************************************* * - * FUNCTION: acpi_unload_table + * FUNCTION: acpi_get_table * - * PARAMETERS: table_type - Type of table to be unloaded + * PARAMETERS: Signature - ACPI signature of needed table + * Instance - Which instance (for SSDTs) + * out_table - Where the pointer to the table is returned * - * RETURN: Status + * RETURN: Status and pointer to table * - * DESCRIPTION: This routine is used to force the unload of a table + * DESCRIPTION: Finds and verifies an ACPI table. * - ******************************************************************************/ -acpi_status acpi_unload_table(acpi_table_type table_type) + *****************************************************************************/ +acpi_status +acpi_get_table(char *signature, + acpi_native_uint instance, struct acpi_table_header ** out_table) { - struct acpi_table_desc *table_desc; - - ACPI_FUNCTION_TRACE(acpi_unload_table); - - /* Parameter validation */ + acpi_native_uint i; + acpi_native_uint j; + acpi_status status; - if (table_type > ACPI_TABLE_ID_MAX) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } + /* + * Walk the root table list + */ + for (i = 0, j = 0; i < acpi_gbl_root_table_list.count; i++) { + if (!ACPI_COMPARE_NAME + (&(acpi_gbl_root_table_list.tables[i].signature), + signature)) { + continue; + } - /* Find all tables of the requested type */ + if (++j < instance) { + continue; + } - table_desc = acpi_gbl_table_lists[table_type].next; - if (!table_desc) { - return_ACPI_STATUS(AE_NOT_EXIST); - } + status = + acpi_tb_verify_table(&acpi_gbl_root_table_list.tables[i]); + if (ACPI_SUCCESS(status)) { + *out_table = acpi_gbl_root_table_list.tables[i].pointer; + } - while (table_desc) { - /* - * Delete all namespace objects owned by this table. Note that these - * objects can appear anywhere in the namespace by virtue of the AML - * "Scope" operator. Thus, we need to track ownership by an ID, not - * simply a position within the hierarchy - */ - acpi_ns_delete_namespace_by_owner(table_desc->owner_id); - table_desc = table_desc->next; + return (status); } - /* Delete (or unmap) all tables of this type */ - - acpi_tb_delete_tables_by_type(table_type); - return_ACPI_STATUS(AE_OK); + return (AE_NOT_FOUND); } -ACPI_EXPORT_SYMBOL(acpi_unload_table) +ACPI_EXPORT_SYMBOL(acpi_get_table) /******************************************************************************* * - * FUNCTION: acpi_get_table_header + * FUNCTION: acpi_get_table_by_index * - * PARAMETERS: table_type - one of the defined table types - * Instance - the non zero instance of the table, allows - * support for multiple tables of the same type - * see acpi_gbl_acpi_table_flag - * out_table_header - pointer to the struct acpi_table_header if successful + * PARAMETERS: table_index - Table index + * Table - Where the pointer to the table is returned * - * DESCRIPTION: This function is called to get an ACPI table header. The caller - * supplies an pointer to a data area sufficient to contain an ACPI - * struct acpi_table_header structure. + * RETURN: Status and pointer to the table * - * The header contains a length field that can be used to determine - * the size of the buffer needed to contain the entire table. This - * function is not valid for the RSD PTR table since it does not - * have a standard header and is fixed length. + * DESCRIPTION: Obtain a table by an index into the global table list. * ******************************************************************************/ acpi_status -acpi_get_table_header(acpi_table_type table_type, - u32 instance, struct acpi_table_header *out_table_header) +acpi_get_table_by_index(acpi_native_uint table_index, + struct acpi_table_header ** table) { - struct acpi_table_header *tbl_ptr; acpi_status status; - ACPI_FUNCTION_TRACE(acpi_get_table_header); + ACPI_FUNCTION_TRACE(acpi_get_table_by_index); - if ((instance == 0) || - (table_type == ACPI_TABLE_ID_RSDP) || (!out_table_header)) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); - /* Check the table type and instance */ + /* Validate index */ - if ((table_type > ACPI_TABLE_ID_MAX) || - (ACPI_IS_SINGLE_TABLE(acpi_gbl_table_data[table_type].flags) && - instance > 1)) { + if (table_index >= acpi_gbl_root_table_list.count) { + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); return_ACPI_STATUS(AE_BAD_PARAMETER); } - /* Get a pointer to the entire table */ + if (!acpi_gbl_root_table_list.tables[table_index].pointer) { - status = acpi_tb_get_table_ptr(table_type, instance, &tbl_ptr); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } + /* Table is not mapped, map it */ - /* The function will return a NULL pointer if the table is not loaded */ - - if (tbl_ptr == NULL) { - return_ACPI_STATUS(AE_NOT_EXIST); + status = + acpi_tb_verify_table(&acpi_gbl_root_table_list. + tables[table_index]); + if (ACPI_FAILURE(status)) { + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + return_ACPI_STATUS(status); + } } - /* Copy the header to the caller's buffer */ - - ACPI_MEMCPY(ACPI_CAST_PTR(void, out_table_header), - ACPI_CAST_PTR(void, tbl_ptr), - sizeof(struct acpi_table_header)); - - return_ACPI_STATUS(status); + *table = acpi_gbl_root_table_list.tables[table_index].pointer; + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + return_ACPI_STATUS(AE_OK); } -ACPI_EXPORT_SYMBOL(acpi_get_table_header) -#endif /* ACPI_FUTURE_USAGE */ +ACPI_EXPORT_SYMBOL(acpi_get_table_by_index) /******************************************************************************* * - * FUNCTION: acpi_get_table + * FUNCTION: acpi_tb_load_namespace * - * PARAMETERS: table_type - one of the defined table types - * Instance - the non zero instance of the table, allows - * support for multiple tables of the same type - * see acpi_gbl_acpi_table_flag - * ret_buffer - pointer to a structure containing a buffer to - * receive the table + * PARAMETERS: None * * RETURN: Status * - * DESCRIPTION: This function is called to get an ACPI table. The caller - * supplies an out_buffer large enough to contain the entire ACPI - * table. The caller should call the acpi_get_table_header function - * first to determine the buffer size needed. Upon completion - * the out_buffer->Length field will indicate the number of bytes - * copied into the out_buffer->buf_ptr buffer. This table will be - * a complete table including the header. + * DESCRIPTION: Load the namespace from the DSDT and all SSDTs/PSDTs found in + * the RSDT/XSDT. * ******************************************************************************/ -acpi_status -acpi_get_table(acpi_table_type table_type, - u32 instance, struct acpi_buffer *ret_buffer) +static acpi_status acpi_tb_load_namespace(void) { - struct acpi_table_header *tbl_ptr; acpi_status status; - acpi_size table_length; + struct acpi_table_header *table; + acpi_native_uint i; - ACPI_FUNCTION_TRACE(acpi_get_table); + ACPI_FUNCTION_TRACE(tb_load_namespace); - /* Parameter validation */ + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); - if (instance == 0) { - return_ACPI_STATUS(AE_BAD_PARAMETER); + /* + * Load the namespace. The DSDT is required, but any SSDT and PSDT tables + * are optional. + */ + if (!acpi_gbl_root_table_list.count || + !ACPI_COMPARE_NAME(& + (acpi_gbl_root_table_list. + tables[ACPI_TABLE_INDEX_DSDT].signature), + ACPI_SIG_DSDT) + || + ACPI_FAILURE(acpi_tb_verify_table + (&acpi_gbl_root_table_list. + tables[ACPI_TABLE_INDEX_DSDT]))) { + status = AE_NO_ACPI_TABLES; + goto unlock_and_exit; } - status = acpi_ut_validate_buffer(ret_buffer); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + /* + * Find DSDT table + */ + status = + acpi_os_table_override(acpi_gbl_root_table_list. + tables[ACPI_TABLE_INDEX_DSDT].pointer, + &table); + if (ACPI_SUCCESS(status) && table) { + /* + * DSDT table has been found + */ + acpi_tb_delete_table(ACPI_TABLE_INDEX_DSDT); + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].pointer = + table; + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].length = + table->length; + acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].flags = + ACPI_TABLE_ORIGIN_UNKNOWN; + + ACPI_INFO((AE_INFO, "Table DSDT replaced by host OS")); + acpi_tb_print_table_header(0, table); } - /* Check the table type and instance */ + status = + acpi_tb_verify_table(&acpi_gbl_root_table_list. + tables[ACPI_TABLE_INDEX_DSDT]); + if (ACPI_FAILURE(status)) { + + /* A valid DSDT is required */ - if ((table_type > ACPI_TABLE_ID_MAX) || - (ACPI_IS_SINGLE_TABLE(acpi_gbl_table_data[table_type].flags) && - instance > 1)) { - return_ACPI_STATUS(AE_BAD_PARAMETER); + status = AE_NO_ACPI_TABLES; + goto unlock_and_exit; } - /* Get a pointer to the entire table */ + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); - status = acpi_tb_get_table_ptr(table_type, instance, &tbl_ptr); + /* + * Load and parse tables. + */ + status = acpi_ns_load_table(ACPI_TABLE_INDEX_DSDT, acpi_gbl_root_node); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } /* - * acpi_tb_get_table_ptr will return a NULL pointer if the - * table is not loaded. + * Load any SSDT or PSDT tables. Note: Loop leaves tables locked */ - if (tbl_ptr == NULL) { - return_ACPI_STATUS(AE_NOT_EXIST); + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); + for (i = 0; i < acpi_gbl_root_table_list.count; ++i) { + if ((!ACPI_COMPARE_NAME + (&(acpi_gbl_root_table_list.tables[i].signature), + ACPI_SIG_SSDT) + && + !ACPI_COMPARE_NAME(& + (acpi_gbl_root_table_list.tables[i]. + signature), ACPI_SIG_PSDT)) + || + ACPI_FAILURE(acpi_tb_verify_table + (&acpi_gbl_root_table_list.tables[i]))) { + continue; + } + + /* Ignore errors while loading tables, get as many as possible */ + + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + (void)acpi_ns_load_table(i, acpi_gbl_root_node); + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); } - /* Get the table length */ + ACPI_DEBUG_PRINT((ACPI_DB_INIT, "ACPI Tables successfully acquired\n")); - if (table_type == ACPI_TABLE_ID_RSDP) { + unlock_and_exit: + (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); + return_ACPI_STATUS(status); +} - /* RSD PTR is the only "table" without a header */ +/******************************************************************************* + * + * FUNCTION: acpi_load_tables + * + * PARAMETERS: None + * + * RETURN: Status + * + * DESCRIPTION: Load the ACPI tables from the RSDT/XSDT + * + ******************************************************************************/ - table_length = sizeof(struct rsdp_descriptor); - } else { - table_length = (acpi_size) tbl_ptr->length; - } +acpi_status acpi_load_tables(void) +{ + acpi_status status; - /* Validate/Allocate/Clear caller buffer */ + ACPI_FUNCTION_TRACE(acpi_load_tables); - status = acpi_ut_initialize_buffer(ret_buffer, table_length); + /* + * Load the namespace from the tables + */ + status = acpi_tb_load_namespace(); if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + ACPI_EXCEPTION((AE_INFO, status, + "While loading namespace from ACPI tables")); } - /* Copy the table to the buffer */ - - ACPI_MEMCPY(ACPI_CAST_PTR(void, ret_buffer->pointer), - ACPI_CAST_PTR(void, tbl_ptr), table_length); - - return_ACPI_STATUS(AE_OK); + return_ACPI_STATUS(status); } -ACPI_EXPORT_SYMBOL(acpi_get_table) +ACPI_EXPORT_SYMBOL(acpi_load_tables) diff --git a/drivers/acpi/tables/tbxfroot.c b/drivers/acpi/tables/tbxfroot.c index da2648b..5c6e882 100644 --- a/drivers/acpi/tables/tbxfroot.c +++ b/drivers/acpi/tables/tbxfroot.c @@ -48,16 +48,15 @@ ACPI_MODULE_NAME("tbxfroot") /* Local prototypes */ -static acpi_status -acpi_tb_find_rsdp(struct acpi_table_desc *table_info, u32 flags); - static u8 *acpi_tb_scan_memory_for_rsdp(u8 * start_address, u32 length); +static acpi_status acpi_tb_validate_rsdp(struct acpi_table_rsdp *rsdp); + /******************************************************************************* * * FUNCTION: acpi_tb_validate_rsdp * - * PARAMETERS: Rsdp - Pointer to unvalidated RSDP + * PARAMETERS: Rsdp - Pointer to unvalidated RSDP * * RETURN: Status * @@ -65,14 +64,18 @@ static u8 *acpi_tb_scan_memory_for_rsdp(u8 * start_address, u32 length); * ******************************************************************************/ -acpi_status acpi_tb_validate_rsdp(struct rsdp_descriptor *rsdp) +static acpi_status acpi_tb_validate_rsdp(struct acpi_table_rsdp *rsdp) { ACPI_FUNCTION_ENTRY(); /* - * The signature and checksum must both be correct + * The signature and checksum must both be correct + * + * Note: Sometimes there exists more than one RSDP in memory; the valid + * RSDP has a valid checksum, all others have an invalid checksum. */ - if (ACPI_STRNCMP((char *)rsdp, RSDP_SIG, sizeof(RSDP_SIG) - 1) != 0) { + if (ACPI_STRNCMP((char *)rsdp, ACPI_SIG_RSDP, sizeof(ACPI_SIG_RSDP) - 1) + != 0) { /* Nope, BAD Signature */ @@ -81,330 +84,141 @@ acpi_status acpi_tb_validate_rsdp(struct rsdp_descriptor *rsdp) /* Check the standard checksum */ - if (acpi_tb_sum_table(rsdp, ACPI_RSDP_CHECKSUM_LENGTH) != 0) { + if (acpi_tb_checksum((u8 *) rsdp, ACPI_RSDP_CHECKSUM_LENGTH) != 0) { return (AE_BAD_CHECKSUM); } /* Check extended checksum if table version >= 2 */ if ((rsdp->revision >= 2) && - (acpi_tb_sum_table(rsdp, ACPI_RSDP_XCHECKSUM_LENGTH) != 0)) { + (acpi_tb_checksum((u8 *) rsdp, ACPI_RSDP_XCHECKSUM_LENGTH) != 0)) { return (AE_BAD_CHECKSUM); } return (AE_OK); } +#if ACPI_MACHINE_WIDTH != 16 + /******************************************************************************* * - * FUNCTION: acpi_tb_find_table - * - * PARAMETERS: Signature - String with ACPI table signature - * oem_id - String with the table OEM ID - * oem_table_id - String with the OEM Table ID - * table_ptr - Where the table pointer is returned - * - * RETURN: Status + * FUNCTION: acpi_tb_find_rsdp * - * DESCRIPTION: Find an ACPI table (in the RSDT/XSDT) that matches the - * Signature, OEM ID and OEM Table ID. + * PARAMETERS: table_address - Where the table pointer is returned * - ******************************************************************************/ - -acpi_status -acpi_tb_find_table(char *signature, - char *oem_id, - char *oem_table_id, struct acpi_table_header ** table_ptr) -{ - acpi_status status; - struct acpi_table_header *table; - - ACPI_FUNCTION_TRACE(tb_find_table); - - /* Validate string lengths */ - - if ((ACPI_STRLEN(signature) > ACPI_NAME_SIZE) || - (ACPI_STRLEN(oem_id) > sizeof(table->oem_id)) || - (ACPI_STRLEN(oem_table_id) > sizeof(table->oem_table_id))) { - return_ACPI_STATUS(AE_AML_STRING_LIMIT); - } - - if (ACPI_COMPARE_NAME(signature, DSDT_SIG)) { - /* - * The DSDT pointer is contained in the FADT, not the RSDT. - * This code should suffice, because the only code that would perform - * a "find" on the DSDT is the data_table_region() AML opcode -- in - * which case, the DSDT is guaranteed to be already loaded. - * If this becomes insufficient, the FADT will have to be found first. - */ - if (!acpi_gbl_DSDT) { - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - table = acpi_gbl_DSDT; - } else { - /* Find the table */ - - status = acpi_get_firmware_table(signature, 1, - ACPI_LOGICAL_ADDRESSING, - &table); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - } - - /* Check oem_id and oem_table_id */ - - if ((oem_id[0] && - ACPI_STRNCMP(oem_id, table->oem_id, - sizeof(table->oem_id))) || - (oem_table_id[0] && - ACPI_STRNCMP(oem_table_id, table->oem_table_id, - sizeof(table->oem_table_id)))) { - return_ACPI_STATUS(AE_AML_NAME_NOT_FOUND); - } - - ACPI_DEBUG_PRINT((ACPI_DB_TABLES, "Found table [%4.4s]\n", - table->signature)); - - *table_ptr = table; - return_ACPI_STATUS(AE_OK); -} - -/******************************************************************************* - * - * FUNCTION: acpi_get_firmware_table + * RETURN: Status, RSDP physical address * - * PARAMETERS: Signature - Any ACPI table signature - * Instance - the non zero instance of the table, allows - * support for multiple tables of the same type - * Flags - Physical/Virtual support - * table_pointer - Where a buffer containing the table is - * returned + * DESCRIPTION: Search lower 1_mbyte of memory for the root system descriptor + * pointer structure. If it is found, set *RSDP to point to it. * - * RETURN: Status + * NOTE1: The RSDP must be either in the first 1_k of the Extended + * BIOS Data Area or between E0000 and FFFFF (From ACPI Spec.) + * Only a 32-bit physical address is necessary. * - * DESCRIPTION: This function is called to get an ACPI table. A buffer is - * allocated for the table and returned in table_pointer. - * This table will be a complete table including the header. + * NOTE2: This function is always available, regardless of the + * initialization state of the rest of ACPI. * ******************************************************************************/ -acpi_status -acpi_get_firmware_table(acpi_string signature, - u32 instance, - u32 flags, struct acpi_table_header **table_pointer) +acpi_status acpi_find_root_pointer(acpi_native_uint * table_address) { - acpi_status status; - struct acpi_pointer address; - struct acpi_table_header *header = NULL; - struct acpi_table_desc *table_info = NULL; - struct acpi_table_desc *rsdt_info; - u32 table_count; - u32 i; - u32 j; - - ACPI_FUNCTION_TRACE(acpi_get_firmware_table); - - /* - * Ensure that at least the table manager is initialized. We don't - * require that the entire ACPI subsystem is up for this interface. - * If we have a buffer, we must have a length too - */ - if ((instance == 0) || (!signature) || (!table_pointer)) { - return_ACPI_STATUS(AE_BAD_PARAMETER); - } - - /* Ensure that we have a RSDP */ - - if (!acpi_gbl_RSDP) { - - /* Get the RSDP */ - - status = acpi_os_get_root_pointer(flags, &address); - if (ACPI_FAILURE(status)) { - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "RSDP not found\n")); - return_ACPI_STATUS(AE_NO_ACPI_TABLES); - } - - /* Map and validate the RSDP */ - - if ((flags & ACPI_MEMORY_MODE) == ACPI_LOGICAL_ADDRESSING) { - status = acpi_os_map_memory(address.pointer.physical, - sizeof(struct - rsdp_descriptor), - (void *)&acpi_gbl_RSDP); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - } else { - acpi_gbl_RSDP = address.pointer.logical; - } - - /* The RDSP signature and checksum must both be correct */ - - status = acpi_tb_validate_rsdp(acpi_gbl_RSDP); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - } - - /* Get the RSDT address via the RSDP */ - - acpi_tb_get_rsdt_address(&address); - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "RSDP located at %p, RSDT physical=%8.8X%8.8X\n", - acpi_gbl_RSDP, - ACPI_FORMAT_UINT64(address.pointer.value))); + u8 *table_ptr; + u8 *mem_rover; + u32 physical_address; - /* Insert processor_mode flags */ + ACPI_FUNCTION_TRACE(acpi_find_root_pointer); - address.pointer_type |= flags; + /* 1a) Get the location of the Extended BIOS Data Area (EBDA) */ - /* Get and validate the RSDT */ + table_ptr = acpi_os_map_memory((acpi_physical_address) + ACPI_EBDA_PTR_LOCATION, + ACPI_EBDA_PTR_LENGTH); + if (!table_ptr) { + ACPI_ERROR((AE_INFO, + "Could not map memory at %8.8X for length %X", + ACPI_EBDA_PTR_LOCATION, ACPI_EBDA_PTR_LENGTH)); - rsdt_info = ACPI_ALLOCATE_ZEROED(sizeof(struct acpi_table_desc)); - if (!rsdt_info) { return_ACPI_STATUS(AE_NO_MEMORY); } - status = acpi_tb_get_table(&address, rsdt_info); - if (ACPI_FAILURE(status)) { - goto cleanup; - } - - status = acpi_tb_validate_rsdt(rsdt_info->pointer); - if (ACPI_FAILURE(status)) { - goto cleanup; - } - - /* Allocate a scratch table header and table descriptor */ - - header = ACPI_ALLOCATE(sizeof(struct acpi_table_header)); - if (!header) { - status = AE_NO_MEMORY; - goto cleanup; - } + ACPI_MOVE_16_TO_32(&physical_address, table_ptr); - table_info = ACPI_ALLOCATE(sizeof(struct acpi_table_desc)); - if (!table_info) { - status = AE_NO_MEMORY; - goto cleanup; - } + /* Convert segment part to physical address */ - /* Get the number of table pointers within the RSDT */ + physical_address <<= 4; + acpi_os_unmap_memory(table_ptr, ACPI_EBDA_PTR_LENGTH); - table_count = - acpi_tb_get_table_count(acpi_gbl_RSDP, rsdt_info->pointer); - address.pointer_type = acpi_gbl_table_flags | flags; + /* EBDA present? */ - /* - * Search the RSDT/XSDT for the correct instance of the - * requested table - */ - for (i = 0, j = 0; i < table_count; i++) { + if (physical_address > 0x400) { /* - * Get the next table pointer, handle RSDT vs. XSDT - * RSDT pointers are 32 bits, XSDT pointers are 64 bits + * 1b) Search EBDA paragraphs (EBDA is required to be a + * minimum of 1_k length) */ - if (acpi_gbl_root_table_type == ACPI_TABLE_TYPE_RSDT) { - address.pointer.value = - (ACPI_CAST_PTR - (struct rsdt_descriptor, - rsdt_info->pointer))->table_offset_entry[i]; - } else { - address.pointer.value = - (ACPI_CAST_PTR - (struct xsdt_descriptor, - rsdt_info->pointer))->table_offset_entry[i]; - } - - /* Get the table header */ + table_ptr = acpi_os_map_memory((acpi_native_uint) + physical_address, + ACPI_EBDA_WINDOW_SIZE); + if (!table_ptr) { + ACPI_ERROR((AE_INFO, + "Could not map memory at %8.8X for length %X", + physical_address, ACPI_EBDA_WINDOW_SIZE)); - status = acpi_tb_get_table_header(&address, header); - if (ACPI_FAILURE(status)) { - goto cleanup; + return_ACPI_STATUS(AE_NO_MEMORY); } - /* Compare table signatures and table instance */ - - if (ACPI_COMPARE_NAME(header->signature, signature)) { - - /* An instance of the table was found */ + mem_rover = + acpi_tb_scan_memory_for_rsdp(table_ptr, + ACPI_EBDA_WINDOW_SIZE); + acpi_os_unmap_memory(table_ptr, ACPI_EBDA_WINDOW_SIZE); - j++; - if (j >= instance) { + if (mem_rover) { - /* Found the correct instance, get the entire table */ + /* Return the physical address */ - status = - acpi_tb_get_table_body(&address, header, - table_info); - if (ACPI_FAILURE(status)) { - goto cleanup; - } + physical_address += + (u32) ACPI_PTR_DIFF(mem_rover, table_ptr); - *table_pointer = table_info->pointer; - goto cleanup; - } + *table_address = physical_address; + return_ACPI_STATUS(AE_OK); } } - /* Did not find the table */ + /* + * 2) Search upper memory: 16-byte boundaries in E0000h-FFFFFh + */ + table_ptr = acpi_os_map_memory((acpi_physical_address) + ACPI_HI_RSDP_WINDOW_BASE, + ACPI_HI_RSDP_WINDOW_SIZE); - status = AE_NOT_EXIST; + if (!table_ptr) { + ACPI_ERROR((AE_INFO, + "Could not map memory at %8.8X for length %X", + ACPI_HI_RSDP_WINDOW_BASE, + ACPI_HI_RSDP_WINDOW_SIZE)); - cleanup: - if (rsdt_info->pointer) { - acpi_os_unmap_memory(rsdt_info->pointer, - (acpi_size) rsdt_info->pointer->length); + return_ACPI_STATUS(AE_NO_MEMORY); } - ACPI_FREE(rsdt_info); - if (header) { - ACPI_FREE(header); - } - if (table_info) { - ACPI_FREE(table_info); - } - return_ACPI_STATUS(status); -} + mem_rover = + acpi_tb_scan_memory_for_rsdp(table_ptr, ACPI_HI_RSDP_WINDOW_SIZE); + acpi_os_unmap_memory(table_ptr, ACPI_HI_RSDP_WINDOW_SIZE); -ACPI_EXPORT_SYMBOL(acpi_get_firmware_table) + if (mem_rover) { -/* TBD: Move to a new file */ -#if ACPI_MACHINE_WIDTH != 16 -/******************************************************************************* - * - * FUNCTION: acpi_find_root_pointer - * - * PARAMETERS: Flags - Logical/Physical addressing - * rsdp_address - Where to place the RSDP address - * - * RETURN: Status, Physical address of the RSDP - * - * DESCRIPTION: Find the RSDP - * - ******************************************************************************/ -acpi_status acpi_find_root_pointer(u32 flags, struct acpi_pointer *rsdp_address) -{ - struct acpi_table_desc table_info; - acpi_status status; - - ACPI_FUNCTION_TRACE(acpi_find_root_pointer); + /* Return the physical address */ - /* Get the RSDP */ + physical_address = (u32) + (ACPI_HI_RSDP_WINDOW_BASE + + ACPI_PTR_DIFF(mem_rover, table_ptr)); - status = acpi_tb_find_rsdp(&table_info, flags); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "RSDP structure not found - Flags=%X", flags)); - - return_ACPI_STATUS(AE_NO_ACPI_TABLES); + *table_address = physical_address; + return_ACPI_STATUS(AE_OK); } - rsdp_address->pointer_type = ACPI_PHYSICAL_POINTER; - rsdp_address->pointer.physical = table_info.physical_address; - return_ACPI_STATUS(AE_OK); + /* A valid RSDP was not found */ + + ACPI_ERROR((AE_INFO, "A valid RSDP was not found")); + return_ACPI_STATUS(AE_NOT_FOUND); } ACPI_EXPORT_SYMBOL(acpi_find_root_pointer) @@ -440,7 +254,7 @@ static u8 *acpi_tb_scan_memory_for_rsdp(u8 * start_address, u32 length) status = acpi_tb_validate_rsdp(ACPI_CAST_PTR - (struct rsdp_descriptor, mem_rover)); + (struct acpi_table_rsdp, mem_rover)); if (ACPI_SUCCESS(status)) { /* Sig and checksum valid, we have found a real RSDP */ @@ -462,188 +276,4 @@ static u8 *acpi_tb_scan_memory_for_rsdp(u8 * start_address, u32 length) return_PTR(NULL); } -/******************************************************************************* - * - * FUNCTION: acpi_tb_find_rsdp - * - * PARAMETERS: table_info - Where the table info is returned - * Flags - Current memory mode (logical vs. - * physical addressing) - * - * RETURN: Status, RSDP physical address - * - * DESCRIPTION: Search lower 1_mbyte of memory for the root system descriptor - * pointer structure. If it is found, set *RSDP to point to it. - * - * NOTE1: The RSDP must be either in the first 1_k of the Extended - * BIOS Data Area or between E0000 and FFFFF (From ACPI Spec.) - * Only a 32-bit physical address is necessary. - * - * NOTE2: This function is always available, regardless of the - * initialization state of the rest of ACPI. - * - ******************************************************************************/ - -static acpi_status -acpi_tb_find_rsdp(struct acpi_table_desc *table_info, u32 flags) -{ - u8 *table_ptr; - u8 *mem_rover; - u32 physical_address; - acpi_status status; - - ACPI_FUNCTION_TRACE(tb_find_rsdp); - - /* - * Scan supports either logical addressing or physical addressing - */ - if ((flags & ACPI_MEMORY_MODE) == ACPI_LOGICAL_ADDRESSING) { - - /* 1a) Get the location of the Extended BIOS Data Area (EBDA) */ - - status = acpi_os_map_memory((acpi_physical_address) - ACPI_EBDA_PTR_LOCATION, - ACPI_EBDA_PTR_LENGTH, - (void *)&table_ptr); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, - "Could not map memory at %8.8X for length %X", - ACPI_EBDA_PTR_LOCATION, - ACPI_EBDA_PTR_LENGTH)); - - return_ACPI_STATUS(status); - } - - ACPI_MOVE_16_TO_32(&physical_address, table_ptr); - - /* Convert segment part to physical address */ - - physical_address <<= 4; - acpi_os_unmap_memory(table_ptr, ACPI_EBDA_PTR_LENGTH); - - /* EBDA present? */ - - if (physical_address > 0x400) { - /* - * 1b) Search EBDA paragraphs (EBDA is required to be a - * minimum of 1_k length) - */ - status = acpi_os_map_memory((acpi_physical_address) - physical_address, - ACPI_EBDA_WINDOW_SIZE, - (void *)&table_ptr); - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, - "Could not map memory at %8.8X for length %X", - physical_address, - ACPI_EBDA_WINDOW_SIZE)); - - return_ACPI_STATUS(status); - } - - mem_rover = acpi_tb_scan_memory_for_rsdp(table_ptr, - ACPI_EBDA_WINDOW_SIZE); - acpi_os_unmap_memory(table_ptr, ACPI_EBDA_WINDOW_SIZE); - - if (mem_rover) { - - /* Return the physical address */ - - physical_address += - (u32) ACPI_PTR_DIFF(mem_rover, table_ptr); - - table_info->physical_address = - (acpi_physical_address) physical_address; - return_ACPI_STATUS(AE_OK); - } - } - - /* - * 2) Search upper memory: 16-byte boundaries in E0000h-FFFFFh - */ - status = acpi_os_map_memory((acpi_physical_address) - ACPI_HI_RSDP_WINDOW_BASE, - ACPI_HI_RSDP_WINDOW_SIZE, - (void *)&table_ptr); - - if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, - "Could not map memory at %8.8X for length %X", - ACPI_HI_RSDP_WINDOW_BASE, - ACPI_HI_RSDP_WINDOW_SIZE)); - - return_ACPI_STATUS(status); - } - - mem_rover = - acpi_tb_scan_memory_for_rsdp(table_ptr, - ACPI_HI_RSDP_WINDOW_SIZE); - acpi_os_unmap_memory(table_ptr, ACPI_HI_RSDP_WINDOW_SIZE); - - if (mem_rover) { - - /* Return the physical address */ - - physical_address = (u32) - (ACPI_HI_RSDP_WINDOW_BASE + - ACPI_PTR_DIFF(mem_rover, table_ptr)); - - table_info->physical_address = - (acpi_physical_address) physical_address; - return_ACPI_STATUS(AE_OK); - } - } - - /* - * Physical addressing - */ - else { - /* 1a) Get the location of the EBDA */ - - ACPI_MOVE_16_TO_32(&physical_address, ACPI_EBDA_PTR_LOCATION); - physical_address <<= 4; /* Convert segment to physical address */ - - /* EBDA present? */ - - if (physical_address > 0x400) { - /* - * 1b) Search EBDA paragraphs (EBDA is required to be a minimum of - * 1_k length) - */ - mem_rover = - acpi_tb_scan_memory_for_rsdp(ACPI_PHYSADDR_TO_PTR - (physical_address), - ACPI_EBDA_WINDOW_SIZE); - if (mem_rover) { - - /* Return the physical address */ - - table_info->physical_address = - ACPI_TO_INTEGER(mem_rover); - return_ACPI_STATUS(AE_OK); - } - } - - /* 2) Search upper memory: 16-byte boundaries in E0000h-FFFFFh */ - - mem_rover = - acpi_tb_scan_memory_for_rsdp(ACPI_PHYSADDR_TO_PTR - (ACPI_HI_RSDP_WINDOW_BASE), - ACPI_HI_RSDP_WINDOW_SIZE); - if (mem_rover) { - - /* Found it, return the physical address */ - - table_info->physical_address = - ACPI_TO_INTEGER(mem_rover); - return_ACPI_STATUS(AE_OK); - } - } - - /* A valid RSDP was not found */ - - ACPI_ERROR((AE_INFO, "No valid RSDP was found")); - return_ACPI_STATUS(AE_NOT_FOUND); -} - #endif diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 1038452..8809306 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -46,8 +46,9 @@ #include #include +ACPI_EXPORT_SYMBOL(acpi_gbl_FADT) #define _COMPONENT ACPI_UTILITIES -ACPI_MODULE_NAME("utglobal") + ACPI_MODULE_NAME("utglobal") /******************************************************************************* * @@ -280,53 +281,6 @@ char acpi_ut_hex_to_ascii_char(acpi_integer integer, u32 position) return (acpi_gbl_hex_to_ascii[(integer >> position) & 0xF]); } -/******************************************************************************* - * - * Table name globals - * - * NOTE: This table includes ONLY the ACPI tables that the subsystem consumes. - * it is NOT an exhaustive list of all possible ACPI tables. All ACPI tables - * that are not used by the subsystem are simply ignored. - * - * Do NOT add any table to this list that is not consumed directly by this - * subsystem (No MADT, ECDT, SBST, etc.) - * - ******************************************************************************/ - -struct acpi_table_list acpi_gbl_table_lists[ACPI_TABLE_ID_MAX + 1]; - -struct acpi_table_support acpi_gbl_table_data[ACPI_TABLE_ID_MAX + 1] = { - /*********** Name, Signature, Global typed pointer Signature size, Type How many allowed?, Contains valid AML? */ - - /* RSDP 0 */ {RSDP_NAME, RSDP_SIG, NULL, sizeof(RSDP_SIG) - 1, - ACPI_TABLE_ROOT | ACPI_TABLE_SINGLE} - , - /* DSDT 1 */ {DSDT_SIG, DSDT_SIG, (void *)&acpi_gbl_DSDT, - sizeof(DSDT_SIG) - 1, - ACPI_TABLE_SECONDARY | ACPI_TABLE_SINGLE | - ACPI_TABLE_EXECUTABLE} - , - /* FADT 2 */ {FADT_SIG, FADT_SIG, (void *)&acpi_gbl_FADT, - sizeof(FADT_SIG) - 1, - ACPI_TABLE_PRIMARY | ACPI_TABLE_SINGLE} - , - /* FACS 3 */ {FACS_SIG, FACS_SIG, (void *)&acpi_gbl_FACS, - sizeof(FACS_SIG) - 1, - ACPI_TABLE_SECONDARY | ACPI_TABLE_SINGLE} - , - /* PSDT 4 */ {PSDT_SIG, PSDT_SIG, NULL, sizeof(PSDT_SIG) - 1, - ACPI_TABLE_PRIMARY | ACPI_TABLE_MULTIPLE | - ACPI_TABLE_EXECUTABLE} - , - /* SSDT 5 */ {SSDT_SIG, SSDT_SIG, NULL, sizeof(SSDT_SIG) - 1, - ACPI_TABLE_PRIMARY | ACPI_TABLE_MULTIPLE | - ACPI_TABLE_EXECUTABLE} - , - /* XSDT 6 */ {XSDT_SIG, XSDT_SIG, NULL, sizeof(RSDT_SIG) - 1, - ACPI_TABLE_ROOT | ACPI_TABLE_SINGLE} - , -}; - /****************************************************************************** * * Event and Hardware globals @@ -751,13 +705,6 @@ void acpi_ut_init_globals(void) return; } - /* ACPI table structure */ - - for (i = 0; i < (ACPI_TABLE_ID_MAX + 1); i++) { - acpi_gbl_table_lists[i].next = NULL; - acpi_gbl_table_lists[i].count = 0; - } - /* Mutex locked flags */ for (i = 0; i < ACPI_NUM_MUTEX; i++) { @@ -784,14 +731,6 @@ void acpi_ut_init_globals(void) acpi_gbl_exception_handler = NULL; acpi_gbl_init_handler = NULL; - /* Global "typed" ACPI table pointers */ - - acpi_gbl_RSDP = NULL; - acpi_gbl_XSDT = NULL; - acpi_gbl_FACS = NULL; - acpi_gbl_FADT = NULL; - acpi_gbl_DSDT = NULL; - /* Global Lock support */ acpi_gbl_global_lock_semaphore = NULL; @@ -801,8 +740,6 @@ void acpi_ut_init_globals(void) /* Miscellaneous variables */ - acpi_gbl_table_flags = ACPI_PHYSICAL_POINTER; - acpi_gbl_rsdp_original_location = 0; acpi_gbl_cm_single_step = FALSE; acpi_gbl_db_terminate_threads = FALSE; acpi_gbl_shutdown = FALSE; diff --git a/drivers/acpi/utilities/utinit.c b/drivers/acpi/utilities/utinit.c index ff76055..2d2c4a3 100644 --- a/drivers/acpi/utilities/utinit.c +++ b/drivers/acpi/utilities/utinit.c @@ -44,6 +44,7 @@ #include #include #include +#include #define _COMPONENT ACPI_UTILITIES ACPI_MODULE_NAME("utinit") @@ -73,8 +74,8 @@ acpi_ut_fadt_register_error(char *register_name, u32 value, u8 offset) { ACPI_WARNING((AE_INFO, - "Invalid FADT value %s=%X at offset %X FADT=%p", - register_name, value, offset, acpi_gbl_FADT)); + "Invalid FADT value %s=%X at offset %X in FADT=%p", + register_name, value, offset, &acpi_gbl_FADT)); } /****************************************************************************** @@ -96,62 +97,70 @@ acpi_status acpi_ut_validate_fadt(void) * Verify Fixed ACPI Description Table fields, * but don't abort on any problems, just display error */ - if (acpi_gbl_FADT->pm1_evt_len < 4) { + if (acpi_gbl_FADT.pm1_event_length < 4) { acpi_ut_fadt_register_error("PM1_EVT_LEN", - (u32) acpi_gbl_FADT->pm1_evt_len, - ACPI_FADT_OFFSET(pm1_evt_len)); + (u32) acpi_gbl_FADT. + pm1_event_length, + ACPI_FADT_OFFSET(pm1_event_length)); } - if (!acpi_gbl_FADT->pm1_cnt_len) { + if (!acpi_gbl_FADT.pm1_control_length) { acpi_ut_fadt_register_error("PM1_CNT_LEN", 0, - ACPI_FADT_OFFSET(pm1_cnt_len)); + ACPI_FADT_OFFSET + (pm1_control_length)); } - if (!acpi_gbl_FADT->xpm1a_evt_blk.address) { + if (!acpi_gbl_FADT.xpm1a_event_block.address) { acpi_ut_fadt_register_error("X_PM1a_EVT_BLK", 0, - ACPI_FADT_OFFSET(xpm1a_evt_blk. + ACPI_FADT_OFFSET(xpm1a_event_block. address)); } - if (!acpi_gbl_FADT->xpm1a_cnt_blk.address) { + if (!acpi_gbl_FADT.xpm1a_control_block.address) { acpi_ut_fadt_register_error("X_PM1a_CNT_BLK", 0, - ACPI_FADT_OFFSET(xpm1a_cnt_blk. - address)); + ACPI_FADT_OFFSET + (xpm1a_control_block.address)); } - if (!acpi_gbl_FADT->xpm_tmr_blk.address) { + if (!acpi_gbl_FADT.xpm_timer_block.address) { acpi_ut_fadt_register_error("X_PM_TMR_BLK", 0, - ACPI_FADT_OFFSET(xpm_tmr_blk. + ACPI_FADT_OFFSET(xpm_timer_block. address)); } - if ((acpi_gbl_FADT->xpm2_cnt_blk.address && - !acpi_gbl_FADT->pm2_cnt_len)) { + if ((acpi_gbl_FADT.xpm2_control_block.address && + !acpi_gbl_FADT.pm2_control_length)) { acpi_ut_fadt_register_error("PM2_CNT_LEN", - (u32) acpi_gbl_FADT->pm2_cnt_len, - ACPI_FADT_OFFSET(pm2_cnt_len)); + (u32) acpi_gbl_FADT. + pm2_control_length, + ACPI_FADT_OFFSET + (pm2_control_length)); } - if (acpi_gbl_FADT->pm_tm_len < 4) { + if (acpi_gbl_FADT.pm_timer_length < 4) { acpi_ut_fadt_register_error("PM_TM_LEN", - (u32) acpi_gbl_FADT->pm_tm_len, - ACPI_FADT_OFFSET(pm_tm_len)); + (u32) acpi_gbl_FADT.pm_timer_length, + ACPI_FADT_OFFSET(pm_timer_length)); } /* Length of GPE blocks must be a multiple of 2 */ - if (acpi_gbl_FADT->xgpe0_blk.address && - (acpi_gbl_FADT->gpe0_blk_len & 1)) { + if (acpi_gbl_FADT.xgpe0_block.address && + (acpi_gbl_FADT.gpe0_block_length & 1)) { acpi_ut_fadt_register_error("(x)GPE0_BLK_LEN", - (u32) acpi_gbl_FADT->gpe0_blk_len, - ACPI_FADT_OFFSET(gpe0_blk_len)); + (u32) acpi_gbl_FADT. + gpe0_block_length, + ACPI_FADT_OFFSET + (gpe0_block_length)); } - if (acpi_gbl_FADT->xgpe1_blk.address && - (acpi_gbl_FADT->gpe1_blk_len & 1)) { + if (acpi_gbl_FADT.xgpe1_block.address && + (acpi_gbl_FADT.gpe1_block_length & 1)) { acpi_ut_fadt_register_error("(x)GPE1_BLK_LEN", - (u32) acpi_gbl_FADT->gpe1_blk_len, - ACPI_FADT_OFFSET(gpe1_blk_len)); + (u32) acpi_gbl_FADT. + gpe1_block_length, + ACPI_FADT_OFFSET + (gpe1_block_length)); } return (AE_OK); @@ -178,7 +187,6 @@ static void acpi_ut_terminate(void) ACPI_FUNCTION_TRACE(ut_terminate); - /* Free global tables, etc. */ /* Free global GPE blocks and related info structures */ gpe_xrupt_info = acpi_gbl_gpe_xrupt_list_head; @@ -239,6 +247,10 @@ void acpi_ut_subsystem_shutdown(void) acpi_ns_terminate(); + /* Delete the ACPI tables */ + + acpi_tb_terminate(); + /* Close the globals */ acpi_ut_terminate(); diff --git a/drivers/acpi/utilities/utmisc.c b/drivers/acpi/utilities/utmisc.c index 6d8a821..47dcf82 100644 --- a/drivers/acpi/utilities/utmisc.c +++ b/drivers/acpi/utilities/utmisc.c @@ -67,9 +67,9 @@ u8 acpi_ut_is_aml_table(struct acpi_table_header *table) /* These are the only tables that contain executable AML */ - if (ACPI_COMPARE_NAME(table->signature, DSDT_SIG) || - ACPI_COMPARE_NAME(table->signature, PSDT_SIG) || - ACPI_COMPARE_NAME(table->signature, SSDT_SIG)) { + if (ACPI_COMPARE_NAME(table->signature, ACPI_SIG_DSDT) || + ACPI_COMPARE_NAME(table->signature, ACPI_SIG_PSDT) || + ACPI_COMPARE_NAME(table->signature, ACPI_SIG_SSDT)) { return (TRUE); } @@ -418,7 +418,7 @@ u32 acpi_ut_dword_byte_swap(u32 value) void acpi_ut_set_integer_width(u8 revision) { - if (revision <= 1) { + if (revision < 2) { /* 32-bit case */ diff --git a/drivers/acpi/utilities/utxface.c b/drivers/acpi/utilities/utxface.c index 3538f69..7ea2981 100644 --- a/drivers/acpi/utilities/utxface.c +++ b/drivers/acpi/utilities/utxface.c @@ -398,7 +398,6 @@ acpi_status acpi_get_system_info(struct acpi_buffer * out_buffer) { struct acpi_system_info *info_ptr; acpi_status status; - u32 i; ACPI_FUNCTION_TRACE(acpi_get_system_info); @@ -431,9 +430,7 @@ acpi_status acpi_get_system_info(struct acpi_buffer * out_buffer) /* Timer resolution - 24 or 32 bits */ - if (!acpi_gbl_FADT) { - info_ptr->timer_resolution = 0; - } else if (acpi_gbl_FADT->tmr_val_ext == 0) { + if (acpi_gbl_FADT.flags & ACPI_FADT_32BIT_TIMER) { info_ptr->timer_resolution = 24; } else { info_ptr->timer_resolution = 32; @@ -449,13 +446,6 @@ acpi_status acpi_get_system_info(struct acpi_buffer * out_buffer) info_ptr->debug_layer = acpi_dbg_layer; info_ptr->debug_level = acpi_dbg_level; - /* Current status of the ACPI tables, per table type */ - - info_ptr->num_table_types = ACPI_TABLE_ID_MAX + 1; - for (i = 0; i < (ACPI_TABLE_ID_MAX + 1); i++) { - info_ptr->table_info[i].count = acpi_gbl_table_lists[i].count; - } - return_ACPI_STATUS(AE_OK); } diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index 7ece213..40f856c 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20060721 +#define ACPI_CA_VERSION 0x20060823 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, @@ -115,6 +115,10 @@ #define ACPI_NUM_OWNERID_MASKS 8 +/* Size of the root table array is increased by this increment */ + +#define ACPI_ROOT_TABLE_SIZE_INCREMENT 4 + /****************************************************************************** * * ACPI Specification constants (Do not change unless the specification changes) @@ -152,6 +156,11 @@ #define ACPI_PATH_SEGMENT_LENGTH 5 /* 4 chars for name + 1 char for separator */ #define ACPI_PATH_SEPARATOR '.' +/* Sizes for ACPI table headers */ + +#define ACPI_OEM_ID_SIZE 6 +#define ACPI_OEM_TABLE_ID_SIZE 8 + /* Constants used in searching for the RSDP in low memory */ #define ACPI_EBDA_PTR_LOCATION 0x0000040E /* Physical Address */ diff --git a/include/acpi/acdispat.h b/include/acpi/acdispat.h index a22fe9c..f0272d4 100644 --- a/include/acpi/acdispat.h +++ b/include/acpi/acdispat.h @@ -210,7 +210,7 @@ acpi_ds_method_error(acpi_status status, struct acpi_walk_state *walk_state); * dsinit */ acpi_status -acpi_ds_initialize_objects(struct acpi_table_desc *table_desc, +acpi_ds_initialize_objects(acpi_native_uint table_index, struct acpi_namespace_node *start_node); /* diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index bf43184..82d42b8 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -140,47 +140,23 @@ ACPI_EXTERN u8 ACPI_INIT_GLOBAL(acpi_gbl_leave_wake_gpes_disabled, TRUE); ****************************************************************************/ /* - * Table pointers. - * Although these pointers are somewhat redundant with the global acpi_table, - * they are convenient because they are typed pointers. + * acpi_gbl_root_table_list is the master list of ACPI tables found in the + * RSDT/XSDT. * - * These tables are single-table only; meaning that there can be at most one - * of each in the system. Each global points to the actual table. + * acpi_gbl_FADT is a local copy of the FADT, converted to a common format. */ -ACPI_EXTERN u32 acpi_gbl_table_flags; -ACPI_EXTERN u32 acpi_gbl_rsdt_table_count; -ACPI_EXTERN struct rsdp_descriptor *acpi_gbl_RSDP; -ACPI_EXTERN struct xsdt_descriptor *acpi_gbl_XSDT; -ACPI_EXTERN struct fadt_descriptor *acpi_gbl_FADT; -ACPI_EXTERN struct acpi_table_header *acpi_gbl_DSDT; -ACPI_EXTERN struct facs_descriptor *acpi_gbl_FACS; -ACPI_EXTERN struct acpi_common_facs acpi_gbl_common_fACS; -/* - * Since there may be multiple SSDTs and PSDTs, a single pointer is not - * sufficient; Therefore, there isn't one! - */ - -/* The root table can be either an RSDT or an XSDT */ - -ACPI_EXTERN u8 acpi_gbl_root_table_type; -#define ACPI_TABLE_TYPE_RSDT 'R' -#define ACPI_TABLE_TYPE_XSDT 'X' +ACPI_EXTERN struct acpi_internal_rsdt acpi_gbl_root_table_list; +ACPI_EXTERN struct acpi_table_fadt acpi_gbl_FADT; /* - * Handle both ACPI 1.0 and ACPI 2.0 Integer widths: - * If we are executing a method that exists in a 32-bit ACPI table, - * use only the lower 32 bits of the (internal) 64-bit Integer. + * Handle both ACPI 1.0 and ACPI 2.0 Integer widths. The integer width is + * determined by the revision of the DSDT: If the DSDT revision is less than + * 2, use only the lower 32 bits of the internal 64-bit Integer. */ ACPI_EXTERN u8 acpi_gbl_integer_bit_width; ACPI_EXTERN u8 acpi_gbl_integer_byte_width; ACPI_EXTERN u8 acpi_gbl_integer_nybble_width; -/* - * ACPI Table info arrays - */ -extern struct acpi_table_list acpi_gbl_table_lists[ACPI_TABLE_ID_MAX + 1]; -extern struct acpi_table_support acpi_gbl_table_data[ACPI_TABLE_ID_MAX + 1]; - /***************************************************************************** * * Mutual exlusion within ACPICA subsystem @@ -188,7 +164,7 @@ extern struct acpi_table_support acpi_gbl_table_data[ACPI_TABLE_ID_MAX + 1]; ****************************************************************************/ /* - * Predefined mutex objects. This array contains the + * Predefined mutex objects. This array contains the * actual OS mutex handles, indexed by the local ACPI_MUTEX_HANDLEs. * (The table maps local handles to the real OS handles) */ diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index d542140..0f12fec 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -51,6 +51,7 @@ #define ACPI_SERIALIZED 0xFF typedef u32 acpi_mutex_handle; +#define ACPI_GLOBAL_LOCK (acpi_semaphore) (-1) /* Total number of aml opcodes defined */ @@ -79,8 +80,8 @@ union acpi_parse_object; * table below also! */ #define ACPI_MTX_INTERPRETER 0 /* AML Interpreter, main lock */ -#define ACPI_MTX_TABLES 1 /* Data for ACPI tables */ -#define ACPI_MTX_NAMESPACE 2 /* ACPI Namespace */ +#define ACPI_MTX_NAMESPACE 1 /* ACPI Namespace */ +#define ACPI_MTX_TABLES 2 /* Data for ACPI tables */ #define ACPI_MTX_EVENTS 3 /* Data for ACPI events */ #define ACPI_MTX_CACHES 4 /* Internal caches, general purposes */ #define ACPI_MTX_MEMORY 5 /* Debug memory tracking lists */ @@ -218,25 +219,35 @@ struct acpi_namespace_node { * ACPI Table Descriptor. One per ACPI table */ struct acpi_table_desc { - struct acpi_table_desc *prev; - struct acpi_table_desc *next; - struct acpi_table_desc *installed_desc; + acpi_physical_address address; struct acpi_table_header *pointer; - u8 *aml_start; - u64 physical_address; - acpi_size length; - u32 aml_length; + u32 length; /* Length fixed at 32 bits */ + union acpi_name_union signature; acpi_owner_id owner_id; - u8 type; - u8 allocation; - u8 loaded_into_namespace; + u8 flags; }; -struct acpi_table_list { - struct acpi_table_desc *next; +struct acpi_internal_rsdt { + struct acpi_table_desc *tables; u32 count; + u32 size; + u8 flags; }; +/* Flags for both structs above */ + +#define ACPI_TABLE_ORIGIN_UNKNOWN (0) +#define ACPI_TABLE_ORIGIN_MAPPED (1) +#define ACPI_TABLE_ORIGIN_ALLOCATED (2) +#define ACPI_TABLE_ORIGIN_MASK (3) +#define ACPI_TABLE_FLAGS_LOADED (4) +#define ACPI_TABLE_FLAGS_ALLOW_RESIZE (8) + +/* Predefined (fixed) table indexes */ + +#define ACPI_TABLE_INDEX_DSDT (0) +#define ACPI_TABLE_INDEX_FACS (1) + struct acpi_find_context { char *search_for; acpi_handle *list; diff --git a/include/acpi/acnamesp.h b/include/acpi/acnamesp.h index 83b52f9..b3b9f0e 100644 --- a/include/acpi/acnamesp.h +++ b/include/acpi/acnamesp.h @@ -82,7 +82,7 @@ acpi_status acpi_ns_initialize_devices(void); acpi_status acpi_ns_load_namespace(void); acpi_status -acpi_ns_load_table(struct acpi_table_desc *table_desc, +acpi_ns_load_table(acpi_native_uint table_index, struct acpi_namespace_node *node); /* @@ -106,11 +106,12 @@ struct acpi_namespace_node *acpi_ns_get_next_node(acpi_object_type type, * nsparse - table parsing */ acpi_status -acpi_ns_parse_table(struct acpi_table_desc *table_desc, - struct acpi_namespace_node *scope); +acpi_ns_parse_table(acpi_native_uint table_index, + struct acpi_namespace_node *start_node); acpi_status -acpi_ns_one_complete_parse(u8 pass_number, struct acpi_table_desc *table_desc); +acpi_ns_one_complete_parse(acpi_native_uint pass_number, + acpi_native_uint table_index); /* * nsaccess - Top-level namespace access diff --git a/include/acpi/acpiosxf.h b/include/acpi/acpiosxf.h index 0cd63bc..9a5ffcf 100644 --- a/include/acpi/acpiosxf.h +++ b/include/acpi/acpiosxf.h @@ -85,7 +85,7 @@ acpi_status acpi_os_terminate(void); /* * ACPI Table interfaces */ -acpi_status acpi_os_get_root_pointer(u32 flags, struct acpi_pointer *address); +acpi_physical_address acpi_os_get_root_pointer(void); acpi_status acpi_os_predefined_override(const struct acpi_predefined_names *init_val, @@ -143,9 +143,7 @@ void acpi_os_release_mutex(acpi_mutex handle); */ void *acpi_os_allocate(acpi_size size); -acpi_status -acpi_os_map_memory(acpi_physical_address physical_address, - acpi_size size, void __iomem ** logical_address); +void __iomem *acpi_os_map_memory(acpi_physical_address where, acpi_native_uint length); void acpi_os_unmap_memory(void __iomem * logical_address, acpi_size size); diff --git a/include/acpi/acpixf.h b/include/acpi/acpixf.h index 8145876..f4b0a81 100644 --- a/include/acpi/acpixf.h +++ b/include/acpi/acpixf.h @@ -51,6 +51,10 @@ /* * Global interfaces */ +acpi_status +acpi_initialize_tables(struct acpi_table_desc *initial_storage, + u32 initial_table_count, u8 allow_resize); + acpi_status acpi_initialize_subsystem(void); acpi_status acpi_enable_subsystem(u32 flags); @@ -92,30 +96,28 @@ void acpi_free(void *address); /* * ACPI table manipulation interfaces */ -acpi_status -acpi_find_root_pointer(u32 flags, struct acpi_pointer *rsdp_address); +acpi_status acpi_reallocate_root_table(void); + +acpi_status acpi_find_root_pointer(acpi_native_uint * rsdp_address); acpi_status acpi_load_tables(void); acpi_status acpi_load_table(struct acpi_table_header *table_ptr); -acpi_status acpi_unload_table_id(acpi_table_type table_type, acpi_owner_id id); +acpi_status acpi_unload_table_id(acpi_owner_id id); -#ifdef ACPI_FUTURE_USAGE -acpi_status acpi_unload_table(acpi_table_type table_type); acpi_status -acpi_get_table_header(acpi_table_type table_type, - u32 instance, struct acpi_table_header *out_table_header); -#endif /* ACPI_FUTURE_USAGE */ +acpi_get_table_header(acpi_string signature, + acpi_native_uint instance, + struct acpi_table_header **out_table_header); acpi_status -acpi_get_table(acpi_table_type table_type, - u32 instance, struct acpi_buffer *ret_buffer); +acpi_get_table(acpi_string signature, + acpi_native_uint instance, struct acpi_table_header **out_table); acpi_status -acpi_get_firmware_table(acpi_string signature, - u32 instance, - u32 flags, struct acpi_table_header **table_pointer); +acpi_get_table_by_index(acpi_native_uint table_index, + struct acpi_table_header **out_table); /* * Namespace and name interfaces diff --git a/include/acpi/acstruct.h b/include/acpi/acstruct.h index 5e8095f..9c800b6 100644 --- a/include/acpi/acstruct.h +++ b/include/acpi/acstruct.h @@ -139,7 +139,8 @@ struct acpi_init_walk_info { u16 buffer_init; u16 package_init; u16 object_count; - struct acpi_table_desc *table_desc; + acpi_owner_id owner_id; + acpi_native_uint table_index; }; struct acpi_get_devices_info { diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 4dbaf02..1737a2f 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -44,105 +44,62 @@ #ifndef __ACTABLES_H__ #define __ACTABLES_H__ -/* Used in acpi_tb_map_acpi_table for size parameter if table header is to be used */ - -#define SIZE_IN_HEADER 0 - -/* - * tbconvrt - Table conversion routines - */ -acpi_status acpi_tb_convert_to_xsdt(struct acpi_table_desc *table_info); - -acpi_status acpi_tb_convert_table_fadt(void); - -acpi_status acpi_tb_build_common_facs(struct acpi_table_desc *table_info); - -u32 -acpi_tb_get_table_count(struct rsdp_descriptor *RSDP, - struct acpi_table_header *RSDT); - /* - * tbget - Table "get" routines + * tbfind - find ACPI table */ acpi_status -acpi_tb_get_table(struct acpi_pointer *address, - struct acpi_table_desc *table_info); - -acpi_status -acpi_tb_get_table_header(struct acpi_pointer *address, - struct acpi_table_header *return_header); - -acpi_status -acpi_tb_get_table_body(struct acpi_pointer *address, - struct acpi_table_header *header, - struct acpi_table_desc *table_info); - -acpi_status -acpi_tb_get_table_ptr(acpi_table_type table_type, - u32 instance, struct acpi_table_header **table_ptr_loc); - -acpi_status acpi_tb_verify_rsdp(struct acpi_pointer *address); - -void acpi_tb_get_rsdt_address(struct acpi_pointer *out_address); - -acpi_status acpi_tb_validate_rsdt(struct acpi_table_header *table_ptr); +acpi_tb_find_table(char *signature, + char *oem_id, + char *oem_table_id, acpi_native_uint * table_index); /* - * tbgetall - get multiple required tables + * tbinstal - Table removal and deletion */ -acpi_status acpi_tb_get_required_tables(void); +acpi_status acpi_tb_resize_root_table_list(void); -/* - * tbinstall - Table installation - */ -acpi_status acpi_tb_install_table(struct acpi_table_desc *table_info); +acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc); acpi_status -acpi_tb_recognize_table(struct acpi_table_desc *table_info, u8 search_type); +acpi_tb_add_table(struct acpi_table_header *table, + acpi_native_uint * table_index); acpi_status -acpi_tb_init_table_descriptor(acpi_table_type table_type, - struct acpi_table_desc *table_info); +acpi_tb_store_table(acpi_physical_address address, + struct acpi_table_header *table, + u32 length, u8 flags, acpi_native_uint * table_index); -/* - * tbremove - Table removal and deletion - */ -void acpi_tb_delete_all_tables(void); +void acpi_tb_delete_table(acpi_native_uint table_index); -void acpi_tb_delete_tables_by_type(acpi_table_type type); +void acpi_tb_terminate(void); -void acpi_tb_delete_single_table(struct acpi_table_desc *table_desc); +void acpi_tb_delete_namespace_by_owner(acpi_native_uint table_index); -struct acpi_table_desc *acpi_tb_uninstall_table(struct acpi_table_desc - *table_desc); +acpi_status acpi_tb_allocate_owner_id(acpi_native_uint table_index); + +acpi_status acpi_tb_release_owner_id(acpi_native_uint table_index); -/* - * tbxfroot - RSDP, RSDT utilities - */ acpi_status -acpi_tb_find_table(char *signature, - char *oem_id, - char *oem_table_id, struct acpi_table_header **table_ptr); +acpi_tb_get_owner_id(acpi_native_uint table_index, acpi_owner_id * owner_id); -acpi_status acpi_tb_get_table_rsdt(void); +u8 acpi_tb_is_table_loaded(acpi_native_uint table_index); -acpi_status acpi_tb_validate_rsdp(struct rsdp_descriptor *rsdp); +void acpi_tb_set_table_loaded_flag(acpi_native_uint table_index, u8 is_loaded); /* - * tbutils - common table utilities + * tbutils - table manager utilities */ -acpi_status acpi_tb_is_table_installed(struct acpi_table_desc *new_table_desc); +void +acpi_tb_print_table_header(acpi_physical_address address, + struct acpi_table_header *header); -acpi_status -acpi_tb_verify_table_checksum(struct acpi_table_header *table_header); +u8 acpi_tb_checksum(u8 * buffer, acpi_native_uint length); -u8 acpi_tb_sum_table(void *buffer, u32 length); +void acpi_tb_convert_fadt(struct acpi_table_fadt *fadt); -u8 acpi_tb_generate_checksum(struct acpi_table_header *table); +acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags); -void acpi_tb_set_checksum(struct acpi_table_header *table); +void *acpi_tb_map(acpi_physical_address address, u32 length, u32 flags); -acpi_status -acpi_tb_validate_table_header(struct acpi_table_header *table_header); +void acpi_tb_unmap(void *pointer, u32 length, u32 flags); #endif /* __ACTABLES_H__ */ diff --git a/include/acpi/actbl.h b/include/acpi/actbl.h index b125cee..b455f54 100644 --- a/include/acpi/actbl.h +++ b/include/acpi/actbl.h @@ -48,15 +48,15 @@ * Values for description table header signatures. Useful because they make * it more difficult to inadvertently type in the wrong signature. */ -#define DSDT_SIG "DSDT" /* Differentiated System Description Table */ -#define FADT_SIG "FACP" /* Fixed ACPI Description Table */ -#define FACS_SIG "FACS" /* Firmware ACPI Control Structure */ -#define PSDT_SIG "PSDT" /* Persistent System Description Table */ -#define RSDP_SIG "RSD PTR " /* Root System Description Pointer */ -#define RSDT_SIG "RSDT" /* Root System Description Table */ -#define XSDT_SIG "XSDT" /* Extended System Description Table */ -#define SSDT_SIG "SSDT" /* Secondary System Description Table */ -#define RSDP_NAME "RSDP" +#define ACPI_SIG_DSDT "DSDT" /* Differentiated System Description Table */ +#define ACPI_SIG_FADT "FACP" /* Fixed ACPI Description Table */ +#define ACPI_SIG_FACS "FACS" /* Firmware ACPI Control Structure */ +#define ACPI_SIG_PSDT "PSDT" /* Persistent System Description Table */ +#define ACPI_SIG_RSDP "RSD PTR " /* Root System Description Pointer */ +#define ACPI_SIG_RSDT "RSDT" /* Root System Description Table */ +#define ACPI_SIG_XSDT "XSDT" /* Extended System Description Table */ +#define ACPI_SIG_SSDT "SSDT" /* Secondary System Description Table */ +#define ACPI_RSDP_NAME "RSDP" /* * All tables and structures must be byte-packed to match the ACPI @@ -83,27 +83,29 @@ * ******************************************************************************/ -#define ACPI_TABLE_HEADER_DEF \ - char signature[4]; /* ASCII table signature */\ - u32 length; /* Length of table in bytes, including this header */\ - u8 revision; /* ACPI Specification minor version # */\ - u8 checksum; /* To make sum of entire table == 0 */\ - char oem_id[6]; /* ASCII OEM identification */\ - char oem_table_id[8]; /* ASCII OEM table identification */\ - u32 oem_revision; /* OEM revision number */\ - char asl_compiler_id[4]; /* ASCII ASL compiler vendor ID */\ - u32 asl_compiler_revision; /* ASL compiler version */ - struct acpi_table_header { -ACPI_TABLE_HEADER_DEF}; + char signature[ACPI_NAME_SIZE]; /* ASCII table signature */ + u32 length; /* Length of table in bytes, including this header */ + u8 revision; /* ACPI Specification minor version # */ + u8 checksum; /* To make sum of entire table == 0 */ + char oem_id[ACPI_OEM_ID_SIZE]; /* ASCII OEM identification */ + char oem_table_id[ACPI_OEM_TABLE_ID_SIZE]; /* ASCII OEM table identification */ + u32 oem_revision; /* OEM revision number */ + char asl_compiler_id[ACPI_NAME_SIZE]; /* ASCII ASL compiler vendor ID */ + u32 asl_compiler_revision; /* ASL compiler version */ +}; /* * GAS - Generic Address Structure (ACPI 2.0+) + * + * Note: Since this structure is used in the ACPI tables, it is byte aligned. + * If misalignment is not supported, access to the Address field must be + * performed with care. */ struct acpi_generic_address { - u8 address_space_id; /* Address space where struct or register exists */ - u8 register_bit_width; /* Size in bits of given register */ - u8 register_bit_offset; /* Bit offset within the register */ + u8 space_id; /* Address space where struct or register exists */ + u8 bit_width; /* Size in bits of given register */ + u8 bit_offset; /* Bit offset within the register */ u8 access_width; /* Minimum Access size (ACPI 3.0) */ u64 address; /* 64-bit address of struct or register */ }; @@ -114,10 +116,10 @@ struct acpi_generic_address { * ******************************************************************************/ -struct rsdp_descriptor { +struct acpi_table_rsdp { char signature[8]; /* ACPI signature, contains "RSD PTR " */ u8 checksum; /* ACPI 1.0 checksum */ - char oem_id[6]; /* OEM identification */ + char oem_id[ACPI_OEM_ID_SIZE]; /* OEM identification */ u8 revision; /* Must be (0) for ACPI 1.0 or (2) for ACPI 2.0+ */ u32 rsdt_physical_address; /* 32-bit physical address of the RSDT */ u32 length; /* Table length in bytes, including header (ACPI 2.0+) */ @@ -134,12 +136,14 @@ struct rsdp_descriptor { * ******************************************************************************/ -struct rsdt_descriptor { - ACPI_TABLE_HEADER_DEF u32 table_offset_entry[1]; /* Array of pointers to ACPI tables */ +struct acpi_table_rsdt { + struct acpi_table_header header; /* Common ACPI table header */ + u32 table_offset_entry[1]; /* Array of pointers to ACPI tables */ }; -struct xsdt_descriptor { - ACPI_TABLE_HEADER_DEF u64 table_offset_entry[1]; /* Array of pointers to ACPI tables */ +struct acpi_table_xsdt { + struct acpi_table_header header; /* Common ACPI table header */ + u64 table_offset_entry[1]; /* Array of pointers to ACPI tables */ }; /******************************************************************************* @@ -148,36 +152,27 @@ struct xsdt_descriptor { * ******************************************************************************/ -struct facs_descriptor { +struct acpi_table_facs { char signature[4]; /* ASCII table signature */ u32 length; /* Length of structure, in bytes */ u32 hardware_signature; /* Hardware configuration signature */ u32 firmware_waking_vector; /* 32-bit physical address of the Firmware Waking Vector */ u32 global_lock; /* Global Lock for shared hardware resources */ - - /* Flags (32 bits) */ - - u8 S4bios_f:1; /* 00: S4BIOS support is present */ - u8:7; /* 01-07: Reserved, must be zero */ - u8 reserved1[3]; /* 08-31: Reserved, must be zero */ - + u32 flags; u64 xfirmware_waking_vector; /* 64-bit version of the Firmware Waking Vector (ACPI 2.0+) */ u8 version; /* Version of this table (ACPI 2.0+) */ u8 reserved[31]; /* Reserved, must be zero */ }; +/* Flag macros */ + +#define ACPI_FACS_S4_BIOS_PRESENT (1) /* 00: S4BIOS support is present */ + +/* Global lock flags */ + #define ACPI_GLOCK_PENDING 0x01 /* 00: Pending global lock ownership */ #define ACPI_GLOCK_OWNED 0x02 /* 01: Global lock is owned */ -/* - * Common FACS - This is a version-independent FACS structure used for internal use only - */ -struct acpi_common_facs { - u32 *global_lock; - u64 *firmware_waking_vector; - u8 vector_width; -}; - /******************************************************************************* * * FADT - Fixed ACPI Description Table (Signature "FACP") @@ -186,121 +181,98 @@ struct acpi_common_facs { /* Fields common to all versions of the FADT */ -#define ACPI_FADT_COMMON \ - ACPI_TABLE_HEADER_DEF \ - u32 V1_firmware_ctrl; /* 32-bit physical address of FACS */ \ - u32 V1_dsdt; /* 32-bit physical address of DSDT */ \ - u8 reserved1; /* System Interrupt Model isn't used in ACPI 2.0*/ \ - u8 prefer_PM_profile; /* Conveys preferred power management profile to OSPM. */ \ - u16 sci_int; /* System vector of SCI interrupt */ \ - u32 smi_cmd; /* Port address of SMI command port */ \ - u8 acpi_enable; /* Value to write to smi_cmd to enable ACPI */ \ - u8 acpi_disable; /* Value to write to smi_cmd to disable ACPI */ \ - u8 S4bios_req; /* Value to write to SMI CMD to enter S4BIOS state */ \ - u8 pstate_cnt; /* Processor performance state control*/ \ - u32 V1_pm1a_evt_blk; /* Port address of Power Mgt 1a Event Reg Blk */ \ - u32 V1_pm1b_evt_blk; /* Port address of Power Mgt 1b Event Reg Blk */ \ - u32 V1_pm1a_cnt_blk; /* Port address of Power Mgt 1a Control Reg Blk */ \ - u32 V1_pm1b_cnt_blk; /* Port address of Power Mgt 1b Control Reg Blk */ \ - u32 V1_pm2_cnt_blk; /* Port address of Power Mgt 2 Control Reg Blk */ \ - u32 V1_pm_tmr_blk; /* Port address of Power Mgt Timer Ctrl Reg Blk */ \ - u32 V1_gpe0_blk; /* Port addr of General Purpose acpi_event 0 Reg Blk */ \ - u32 V1_gpe1_blk; /* Port addr of General Purpose acpi_event 1 Reg Blk */ \ - u8 pm1_evt_len; /* Byte Length of ports at pm1_x_evt_blk */ \ - u8 pm1_cnt_len; /* Byte Length of ports at pm1_x_cnt_blk */ \ - u8 pm2_cnt_len; /* Byte Length of ports at pm2_cnt_blk */ \ - u8 pm_tm_len; /* Byte Length of ports at pm_tm_blk */ \ - u8 gpe0_blk_len; /* Byte Length of ports at gpe0_blk */ \ - u8 gpe1_blk_len; /* Byte Length of ports at gpe1_blk */ \ - u8 gpe1_base; /* Offset in gpe model where gpe1 events start */ \ - u8 cst_cnt; /* Support for the _CST object and C States change notification.*/ \ - u16 plvl2_lat; /* Worst case HW latency to enter/exit C2 state */ \ - u16 plvl3_lat; /* Worst case HW latency to enter/exit C3 state */ \ - u16 flush_size; /* Processor's memory cache line width, in bytes */ \ - u16 flush_stride; /* Number of flush strides that need to be read */ \ - u8 duty_offset; /* Processor's duty cycle index in processor's P_CNT reg*/ \ - u8 duty_width; /* Processor's duty cycle value bit width in P_CNT register.*/ \ - u8 day_alrm; /* Index to day-of-month alarm in RTC CMOS RAM */ \ - u8 mon_alrm; /* Index to month-of-year alarm in RTC CMOS RAM */ \ - u8 century; /* Index to century in RTC CMOS RAM */ \ - u16 iapc_boot_arch; /* IA-PC Boot Architecture Flags. See Table 5-10 for description*/ \ - u8 reserved2; /* Reserved, must be zero */ - -/* - * ACPI 2.0+ FADT - */ -struct fadt_descriptor { - ACPI_FADT_COMMON - /* Flags (32 bits) */ - u8 wb_invd:1; /* 00: The wbinvd instruction works properly */ - u8 wb_invd_flush:1; /* 01: The wbinvd flushes but does not invalidate */ - u8 proc_c1:1; /* 02: All processors support C1 state */ - u8 plvl2_up:1; /* 03: C2 state works on MP system */ - u8 pwr_button:1; /* 04: Power button is handled as a generic feature */ - u8 sleep_button:1; /* 05: Sleep button is handled as a generic feature, or not present */ - u8 fixed_rTC:1; /* 06: RTC wakeup stat not in fixed register space */ - u8 rtcs4:1; /* 07: RTC wakeup stat not possible from S4 */ - u8 tmr_val_ext:1; /* 08: tmr_val is 32 bits 0=24-bits */ - u8 dock_cap:1; /* 09: Docking supported */ - u8 reset_reg_sup:1; /* 10: System reset via the FADT RESET_REG supported */ - u8 sealed_case:1; /* 11: No internal expansion capabilities and case is sealed */ - u8 headless:1; /* 12: No local video capabilities or local input devices */ - u8 cpu_sw_sleep:1; /* 13: Must execute native instruction after writing SLP_TYPx register */ - - u8 pci_exp_wak:1; /* 14: System supports PCIEXP_WAKE (STS/EN) bits (ACPI 3.0) */ - u8 use_platform_clock:1; /* 15: OSPM should use platform-provided timer (ACPI 3.0) */ - u8 S4rtc_sts_valid:1; /* 16: Contents of RTC_STS valid after S4 wake (ACPI 3.0) */ - u8 remote_power_on_capable:1; /* 17: System is compatible with remote power on (ACPI 3.0) */ - u8 force_apic_cluster_model:1; /* 18: All local APICs must use cluster model (ACPI 3.0) */ - u8 force_apic_physical_destination_mode:1; /* 19: All local x_aPICs must use physical dest mode (ACPI 3.0) */ - u8:4; /* 20-23: Reserved, must be zero */ - u8 reserved3; /* 24-31: Reserved, must be zero */ - +struct acpi_table_fadt { + struct acpi_table_header header; /* Common ACPI table header */ + u32 facs; /* 32-bit physical address of FACS */ + u32 dsdt; /* 32-bit physical address of DSDT */ + u8 model; /* System Interrupt Model (ACPI 1.0) not used in ACPI 2.0+ */ + u8 preferred_profile; /* Conveys preferred power management profile to OSPM. */ + u16 sci_interrupt; /* System vector of SCI interrupt */ + u32 smi_command; /* Port address of SMI command port */ + u8 acpi_enable; /* Value to write to smi_cmd to enable ACPI */ + u8 acpi_disable; /* Value to write to smi_cmd to disable ACPI */ + u8 S4bios_request; /* Value to write to SMI CMD to enter S4BIOS state */ + u8 pstate_control; /* Processor performance state control */ + u32 pm1a_event_block; /* Port address of Power Mgt 1a Event Reg Blk */ + u32 pm1b_event_block; /* Port address of Power Mgt 1b Event Reg Blk */ + u32 pm1a_control_block; /* Port address of Power Mgt 1a Control Reg Blk */ + u32 pm1b_control_block; /* Port address of Power Mgt 1b Control Reg Blk */ + u32 pm2_control_block; /* Port address of Power Mgt 2 Control Reg Blk */ + u32 pm_timer_block; /* Port address of Power Mgt Timer Ctrl Reg Blk */ + u32 gpe0_block; /* Port addr of General Purpose acpi_event 0 Reg Blk */ + u32 gpe1_block; /* Port addr of General Purpose acpi_event 1 Reg Blk */ + u8 pm1_event_length; /* Byte Length of ports at pm1_x_evt_blk */ + u8 pm1_control_length; /* Byte Length of ports at pm1_x_cnt_blk */ + u8 pm2_control_length; /* Byte Length of ports at pm2_cnt_blk */ + u8 pm_timer_length; /* Byte Length of ports at pm_tmr_blk */ + u8 gpe0_block_length; /* Byte Length of ports at gpe0_blk */ + u8 gpe1_block_length; /* Byte Length of ports at gpe1_blk */ + u8 gpe1_base; /* Offset in gpe model where gpe1 events start */ + u8 cst_control; /* Support for the _CST object and C States change notification. */ + u16 C2latency; /* Worst case HW latency to enter/exit C2 state */ + u16 C3latency; /* Worst case HW latency to enter/exit C3 state */ + u16 flush_size; /* Processor's memory cache line width, in bytes */ + u16 flush_stride; /* Number of flush strides that need to be read */ + u8 duty_offset; /* Processor's duty cycle index in processor's P_CNT reg */ + u8 duty_width; /* Processor's duty cycle value bit width in P_CNT register. */ + u8 day_alarm; /* Index to day-of-month alarm in RTC CMOS RAM */ + u8 month_alarm; /* Index to month-of-year alarm in RTC CMOS RAM */ + u8 century; /* Index to century in RTC CMOS RAM */ + u16 boot_flags; /* IA-PC Boot Architecture Flags. See Table 5-10 for description */ + u8 reserved; /* Reserved, must be zero */ + u32 flags; /* Miscellaneous flag bits */ struct acpi_generic_address reset_register; /* Reset register address in GAS format */ u8 reset_value; /* Value to write to the reset_register port to reset the system */ u8 reserved4[3]; /* These three bytes must be zero */ - u64 xfirmware_ctrl; /* 64-bit physical address of FACS */ + u64 Xfacs; /* 64-bit physical address of FACS */ u64 Xdsdt; /* 64-bit physical address of DSDT */ - struct acpi_generic_address xpm1a_evt_blk; /* Extended Power Mgt 1a acpi_event Reg Blk address */ - struct acpi_generic_address xpm1b_evt_blk; /* Extended Power Mgt 1b acpi_event Reg Blk address */ - struct acpi_generic_address xpm1a_cnt_blk; /* Extended Power Mgt 1a Control Reg Blk address */ - struct acpi_generic_address xpm1b_cnt_blk; /* Extended Power Mgt 1b Control Reg Blk address */ - struct acpi_generic_address xpm2_cnt_blk; /* Extended Power Mgt 2 Control Reg Blk address */ - struct acpi_generic_address xpm_tmr_blk; /* Extended Power Mgt Timer Ctrl Reg Blk address */ - struct acpi_generic_address xgpe0_blk; /* Extended General Purpose acpi_event 0 Reg Blk address */ - struct acpi_generic_address xgpe1_blk; /* Extended General Purpose acpi_event 1 Reg Blk address */ + struct acpi_generic_address xpm1a_event_block; /* Extended Power Mgt 1a acpi_event Reg Blk address */ + struct acpi_generic_address xpm1b_event_block; /* Extended Power Mgt 1b acpi_event Reg Blk address */ + struct acpi_generic_address xpm1a_control_block; /* Extended Power Mgt 1a Control Reg Blk address */ + struct acpi_generic_address xpm1b_control_block; /* Extended Power Mgt 1b Control Reg Blk address */ + struct acpi_generic_address xpm2_control_block; /* Extended Power Mgt 2 Control Reg Blk address */ + struct acpi_generic_address xpm_timer_block; /* Extended Power Mgt Timer Ctrl Reg Blk address */ + struct acpi_generic_address xgpe0_block; /* Extended General Purpose acpi_event 0 Reg Blk address */ + struct acpi_generic_address xgpe1_block; /* Extended General Purpose acpi_event 1 Reg Blk address */ }; -/* - * "Down-revved" ACPI 2.0 FADT descriptor - * Defined here to allow compiler to generate the length of the struct - */ -struct fadt_descriptor_rev2_minus { - ACPI_FADT_COMMON u32 flags; - struct acpi_generic_address reset_register; /* Reset register address in GAS format */ - u8 reset_value; /* Value to write to the reset_register port to reset the system. */ - u8 reserved7[3]; /* Reserved, must be zero */ -}; +/* FADT flags */ + +#define ACPI_FADT_WBINVD (1) /* 00: The wbinvd instruction works properly */ +#define ACPI_FADT_WBINVD_FLUSH (1<<1) /* 01: The wbinvd flushes but does not invalidate */ +#define ACPI_FADT_C1_SUPPORTED (1<<2) /* 02: All processors support C1 state */ +#define ACPI_FADT_C2_MP_SUPPORTED (1<<3) /* 03: C2 state works on MP system */ +#define ACPI_FADT_POWER_BUTTON (1<<4) /* 04: Power button is handled as a generic feature */ +#define ACPI_FADT_SLEEP_BUTTON (1<<5) /* 05: Sleep button is handled as a generic feature, or not present */ +#define ACPI_FADT_FIXED_RTC (1<<6) /* 06: RTC wakeup stat not in fixed register space */ +#define ACPI_FADT_S4_RTC_WAKE (1<<7) /* 07: RTC wakeup stat not possible from S4 */ +#define ACPI_FADT_32BIT_TIMER (1<<8) /* 08: tmr_val is 32 bits 0=24-bits */ +#define ACPI_FADT_DOCKING_SUPPORTED (1<<9) /* 09: Docking supported */ +#define ACPI_FADT_RESET_REGISTER (1<<10) /* 10: System reset via the FADT RESET_REG supported */ +#define ACPI_FADT_SEALED_CASE (1<<11) /* 11: No internal expansion capabilities and case is sealed */ +#define ACPI_FADT_HEADLESS (1<<12) /* 12: No local video capabilities or local input devices */ +#define ACPI_FADT_SLEEP_TYPE (1<<13) /* 13: Must execute native instruction after writing SLP_TYPx register */ +#define ACPI_FADT_PCI_EXPRESS_WAKE (1<<14) /* 14: System supports PCIEXP_WAKE (STS/EN) bits (ACPI 3.0) */ +#define ACPI_FADT_PLATFORM_CLOCK (1<<15) /* 15: OSPM should use platform-provided timer (ACPI 3.0) */ +#define ACPI_FADT_S4_RTC_VALID (1<<16) /* 16: Contents of RTC_STS valid after S4 wake (ACPI 3.0) */ +#define ACPI_FADT_REMOTE_POWER_ON (1<<17) /* 17: System is compatible with remote power on (ACPI 3.0) */ +#define ACPI_FADT_APIC_CLUSTER (1<<18) /* 18: All local APICs must use cluster model (ACPI 3.0) */ +#define ACPI_FADT_APIC_PHYSICAL (1<<19) /* 19: All local x_aPICs must use physical dest mode (ACPI 3.0) */ /* - * ACPI 1.0 FADT - * Defined here to allow compiler to generate the length of the struct + * FADT Prefered Power Management Profiles */ -struct fadt_descriptor_rev1 { - ACPI_FADT_COMMON u32 flags; +enum acpi_prefered_pm_profiles { + PM_UNSPECIFIED = 0, + PM_DESKTOP = 1, + PM_MOBILE = 2, + PM_WORKSTATION = 3, + PM_ENTERPRISE_SERVER = 4, + PM_SOHO_SERVER = 5, + PM_APPLIANCE_PC = 6 }; -/* FADT: Prefered Power Management Profiles */ - -#define PM_UNSPECIFIED 0 -#define PM_DESKTOP 1 -#define PM_MOBILE 2 -#define PM_WORKSTATION 3 -#define PM_ENTERPRISE_SERVER 4 -#define PM_SOHO_SERVER 5 -#define PM_APPLIANCE_PC 6 - -/* FADT: Boot Arch Flags */ +/* FADT Boot Arch Flags */ #define BAF_LEGACY_DEVICES 0x0001 #define BAF_8042_KEYBOARD_CONTROLLER 0x0002 @@ -312,59 +284,11 @@ struct fadt_descriptor_rev1 { #pragma pack() -/* - * This macro is temporary until the table bitfield flag definitions - * are removed and replaced by a Flags field. - */ -#define ACPI_FLAG_OFFSET(d,f,o) (u8) (ACPI_OFFSET (d,f) + \ - sizeof(((d *)0)->f) + o) -/* - * Get the remaining ACPI tables - */ -#include "actbl1.h" +#define ACPI_FADT_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_fadt, f) /* - * ACPI Table information. We save the table address, length, - * and type of memory allocation (mapped or allocated) for each - * table for 1) when we exit, and 2) if a new table is installed + * Get the remaining ACPI tables */ -#define ACPI_MEM_NOT_ALLOCATED 0 -#define ACPI_MEM_ALLOCATED 1 -#define ACPI_MEM_MAPPED 2 - -/* Definitions for the Flags bitfield member of struct acpi_table_support */ - -#define ACPI_TABLE_SINGLE 0x00 -#define ACPI_TABLE_MULTIPLE 0x01 -#define ACPI_TABLE_EXECUTABLE 0x02 - -#define ACPI_TABLE_ROOT 0x00 -#define ACPI_TABLE_PRIMARY 0x10 -#define ACPI_TABLE_SECONDARY 0x20 -#define ACPI_TABLE_ALL 0x30 -#define ACPI_TABLE_TYPE_MASK 0x30 - -/* Data about each known table type */ - -struct acpi_table_support { - char *name; - char *signature; - void **global_ptr; - u8 sig_length; - u8 flags; -}; - -extern u8 acpi_fadt_is_v1; /* is set to 1 if FADT is revision 1, - * needed for certain workarounds */ -/* Macros used to generate offsets to specific table fields */ - -#define ACPI_FACS_OFFSET(f) (u8) ACPI_OFFSET (struct facs_descriptor,f) -#define ACPI_FADT_OFFSET(f) (u8) ACPI_OFFSET (struct fadt_descriptor, f) -#define ACPI_GAS_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_generic_address,f) -#define ACPI_HDR_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_header,f) -#define ACPI_RSDP_OFFSET(f) (u8) ACPI_OFFSET (struct rsdp_descriptor,f) - -#define ACPI_FADT_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct fadt_descriptor,f,o) -#define ACPI_FACS_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct facs_descriptor,f,o) +#include #endif /* __ACTBL_H__ */ diff --git a/include/acpi/actbl1.h b/include/acpi/actbl1.h index 745a644..8ae30b7 100644 --- a/include/acpi/actbl1.h +++ b/include/acpi/actbl1.h @@ -73,12 +73,6 @@ #define ACPI_SIG_TCPA "TCPA" /* Trusted Computing Platform Alliance table */ #define ACPI_SIG_WDRT "WDRT" /* Watchdog Resource Table */ -/* Legacy names */ - -#define APIC_SIG "APIC" /* Multiple APIC Description Table */ -#define BOOT_SIG "BOOT" /* Simple Boot Flag Table */ -#define SBST_SIG "SBST" /* Smart Battery Specification Table */ - /* * All tables must be byte-packed to match the ACPI specification, since * the tables are provided by the system BIOS. @@ -91,6 +85,13 @@ * portable, so do not use any other bitfield types. */ +/* Common Sub-table header (used in MADT, SRAT, etc.) */ + +struct acpi_subtable_header { + u8 type; + u8 length; +}; + /******************************************************************************* * * ASF - Alert Standard Format table (Signature "ASF!") @@ -98,24 +99,27 @@ ******************************************************************************/ struct acpi_table_asf { -ACPI_TABLE_HEADER_DEF}; + struct acpi_table_header header; /* Common ACPI table header */ +}; -#define ACPI_ASF_HEADER_DEF \ - u8 type; \ - u8 reserved; \ - u16 length; +/* ASF subtable header */ struct acpi_asf_header { -ACPI_ASF_HEADER_DEF}; + u8 type; + u8 reserved; + u16 length; +}; -/* Values for Type field */ +/* Values for Type field above */ -#define ASF_INFO 0 -#define ASF_ALERT 1 -#define ASF_CONTROL 2 -#define ASF_BOOT 3 -#define ASF_ADDRESS 4 -#define ASF_RESERVED 5 +enum acpi_asf_type { + ACPI_ASF_TYPE_INFO = 0, + ACPI_ASF_TYPE_ALERT = 1, + ACPI_ASF_TYPE_CONTROL = 2, + ACPI_ASF_TYPE_BOOT = 3, + ACPI_ASF_TYPE_ADDRESS = 4, + ACPI_ASF_TYPE_RESERVED = 5 +}; /* * ASF subtables @@ -124,7 +128,8 @@ ACPI_ASF_HEADER_DEF}; /* 0: ASF Information */ struct acpi_asf_info { - ACPI_ASF_HEADER_DEF u8 min_reset_value; + struct acpi_asf_header header; + u8 min_reset_value; u8 min_poll_interval; u16 system_id; u32 mfg_id; @@ -135,7 +140,8 @@ struct acpi_asf_info { /* 1: ASF Alerts */ struct acpi_asf_alert { - ACPI_ASF_HEADER_DEF u8 assert_mask; + struct acpi_asf_header header; + u8 assert_mask; u8 deassert_mask; u8 alerts; u8 data_length; @@ -145,7 +151,8 @@ struct acpi_asf_alert { /* 2: ASF Remote Control */ struct acpi_asf_remote { - ACPI_ASF_HEADER_DEF u8 controls; + struct acpi_asf_header header; + u8 controls; u8 data_length; u16 reserved2; u8 array[1]; @@ -154,7 +161,8 @@ struct acpi_asf_remote { /* 3: ASF RMCP Boot Options */ struct acpi_asf_rmcp { - ACPI_ASF_HEADER_DEF u8 capabilities[7]; + struct acpi_asf_header header; + u8 capabilities[7]; u8 completion_code; u32 enterprise_id; u8 command; @@ -166,7 +174,8 @@ struct acpi_asf_rmcp { /* 4: ASF Address */ struct acpi_asf_address { - ACPI_ASF_HEADER_DEF u8 eprom_address; + struct acpi_asf_header header; + u8 eprom_address; u8 devices; u8 smbus_addresses[1]; }; @@ -178,7 +187,8 @@ struct acpi_asf_address { ******************************************************************************/ struct acpi_table_boot { - ACPI_TABLE_HEADER_DEF u8 cmos_index; /* Index in CMOS RAM for the boot register */ + struct acpi_table_header header; /* Common ACPI table header */ + u8 cmos_index; /* Index in CMOS RAM for the boot register */ u8 reserved[3]; }; @@ -189,7 +199,8 @@ struct acpi_table_boot { ******************************************************************************/ struct acpi_table_cpep { - ACPI_TABLE_HEADER_DEF u64 reserved; + struct acpi_table_header header; /* Common ACPI table header */ + u64 reserved; }; /* Subtable */ @@ -197,9 +208,9 @@ struct acpi_table_cpep { struct acpi_cpep_polling { u8 type; u8 length; - u8 processor_id; /* Processor ID */ - u8 processor_eid; /* Processor EID */ - u32 polling_interval; /* Polling interval (msec) */ + u8 id; /* Processor ID */ + u8 eid; /* Processor EID */ + u32 interval; /* Polling interval (msec) */ }; /******************************************************************************* @@ -209,7 +220,8 @@ struct acpi_cpep_polling { ******************************************************************************/ struct acpi_table_dbgp { - ACPI_TABLE_HEADER_DEF u8 interface_type; /* 0=full 16550, 1=subset of 16550 */ + struct acpi_table_header header; /* Common ACPI table header */ + u8 type; /* 0=full 16550, 1=subset of 16550 */ u8 reserved[3]; struct acpi_generic_address debug_port; }; @@ -220,12 +232,13 @@ struct acpi_table_dbgp { * ******************************************************************************/ -struct ec_boot_resources { - ACPI_TABLE_HEADER_DEF struct acpi_generic_address ec_control; /* Address of EC command/status register */ - struct acpi_generic_address ec_data; /* Address of EC data register */ +struct acpi_table_ecdt { + struct acpi_table_header header; /* Common ACPI table header */ + struct acpi_generic_address control; /* Address of EC command/status register */ + struct acpi_generic_address data; /* Address of EC data register */ u32 uid; /* Unique ID - must be same as the EC _UID method */ - u8 gpe_bit; /* The GPE for the EC */ - u8 ec_id[1]; /* Full namepath of the EC in the ACPI namespace */ + u8 gpe; /* The GPE for the EC */ + u8 id[1]; /* Full namepath of the EC in the ACPI namespace */ }; /******************************************************************************* @@ -234,22 +247,22 @@ struct ec_boot_resources { * ******************************************************************************/ -struct acpi_hpet_table { - ACPI_TABLE_HEADER_DEF u32 hardware_id; /* Hardware ID of event timer block */ - struct acpi_generic_address base_address; /* Address of event timer block */ - u8 hpet_number; /* HPET sequence number */ - u16 clock_tick; /* Main counter min tick, periodic mode */ - u8 attributes; +struct acpi_table_hpet { + struct acpi_table_header header; /* Common ACPI table header */ + u32 id; /* Hardware ID of event timer block */ + struct acpi_generic_address address; /* Address of event timer block */ + u8 sequence; /* HPET sequence number */ + u16 minimum_tick; /* Main counter min tick, periodic mode */ + u8 flags; }; -#if 0 /* HPET flags to be converted to macros */ -struct { /* Flags (8 bits) */ - u8 page_protect:1; /* 00: No page protection */ - u8 page_protect4:1; /* 01: 4_kB page protected */ - u8 page_protect64:1; /* 02: 64_kB page protected */ - u8:5; /* 03-07: Reserved, must be zero */ -} flags; -#endif +/*! Flags */ + +#define ACPI_HPET_PAGE_PROTECT (1) /* 00: No page protection */ +#define ACPI_HPET_PAGE_PROTECT_4 (1<<1) /* 01: 4KB page protected */ +#define ACPI_HPET_PAGE_PROTECT_64 (1<<2) /* 02: 64KB page protected */ + +/*! [End] no source code translation !*/ /******************************************************************************* * @@ -257,148 +270,159 @@ struct { /* Flags (8 bits) */ * ******************************************************************************/ -struct multiple_apic_table { - ACPI_TABLE_HEADER_DEF u32 local_apic_address; /* Physical address of local APIC */ - - /* Flags (32 bits) */ - - u8 PCATcompat:1; /* 00: System also has dual 8259s */ - u8:7; /* 01-07: Reserved, must be zero */ - u8 reserved1[3]; /* 08-31: Reserved, must be zero */ +struct acpi_table_madt { + struct acpi_table_header header; /* Common ACPI table header */ + u32 address; /* Physical address of local APIC */ + u32 flags; }; -/* Values for MADT PCATCompat */ - -#define DUAL_PIC 0 -#define MULTIPLE_APIC 1 - -/* Common MADT Sub-table header */ - -#define APIC_HEADER_DEF \ - u8 type; \ - u8 length; - -struct apic_header { -APIC_HEADER_DEF}; - -/* Values for Type in struct apic_header */ +/* Flags */ -#define APIC_PROCESSOR 0 -#define APIC_IO 1 -#define APIC_XRUPT_OVERRIDE 2 -#define APIC_NMI 3 -#define APIC_LOCAL_NMI 4 -#define APIC_ADDRESS_OVERRIDE 5 -#define APIC_IO_SAPIC 6 -#define APIC_LOCAL_SAPIC 7 -#define APIC_XRUPT_SOURCE 8 -#define APIC_RESERVED 9 /* 9 and greater are reserved */ +#define ACPI_MADT_PCAT_COMPAT (1) /* 00: System also has dual 8259s */ -/* Flag definitions for MADT sub-tables */ +/* Values for PCATCompat flag */ -#define ACPI_MADT_IFLAGS /* INTI flags (16 bits) */ \ - u8 polarity : 2; /* 00-01: Polarity of APIC I/O input signals */\ - u8 trigger_mode : 2; /* 02-03: Trigger mode of APIC input signals */\ - u8 : 4; /* 04-07: Reserved, must be zero */\ - u8 reserved1; /* 08-15: Reserved, must be zero */ +#define ACPI_MADT_DUAL_PIC 0 +#define ACPI_MADT_MULTIPLE_APIC 1 -#define ACPI_MADT_LFLAGS /* Local Sapic flags (32 bits) */ \ - u8 processor_enabled: 1; /* 00: Processor is usable if set */\ - u8 : 7; /* 01-07: Reserved, must be zero */\ - u8 reserved2[3]; /* 08-31: Reserved, must be zero */ +/* Values for subtable type in struct acpi_subtable_header */ -/* Values for MPS INTI flags */ - -#define POLARITY_CONFORMS 0 -#define POLARITY_ACTIVE_HIGH 1 -#define POLARITY_RESERVED 2 -#define POLARITY_ACTIVE_LOW 3 - -#define TRIGGER_CONFORMS 0 -#define TRIGGER_EDGE 1 -#define TRIGGER_RESERVED 2 -#define TRIGGER_LEVEL 3 +enum acpi_madt_type { + ACPI_MADT_TYPE_LOCAL_APIC = 0, + ACPI_MADT_TYPE_IO_APIC = 1, + ACPI_MADT_TYPE_INTERRUPT_OVERRIDE = 2, + ACPI_MADT_TYPE_NMI_SOURCE = 3, + ACPI_MADT_TYPE_LOCAL_APIC_NMI = 4, + ACPI_MADT_TYPE_LOCAL_APIC_OVERRIDE = 5, + ACPI_MADT_TYPE_IO_SAPIC = 6, + ACPI_MADT_TYPE_LOCAL_SAPIC = 7, + ACPI_MADT_TYPE_INTERRUPT_SOURCE = 8, + ACPI_MADT_TYPE_RESERVED = 9 /* 9 and greater are reserved */ +}; /* - * MADT Sub-tables, correspond to Type in struct apic_header + * MADT Sub-tables, correspond to Type in struct acpi_subtable_header */ -/* 0: processor APIC */ +/* 0: Processor Local APIC */ -struct madt_processor_apic { - APIC_HEADER_DEF u8 processor_id; /* ACPI processor id */ - u8 local_apic_id; /* Processor's local APIC id */ - ACPI_MADT_LFLAGS}; +struct acpi_madt_local_apic { + struct acpi_subtable_header header; + u8 processor_id; /* ACPI processor id */ + u8 id; /* Processor's local APIC id */ + u32 lapic_flags; +}; /* 1: IO APIC */ -struct madt_io_apic { - APIC_HEADER_DEF u8 io_apic_id; /* I/O APIC ID */ +struct acpi_madt_io_apic { + struct acpi_subtable_header header; + u8 id; /* I/O APIC ID */ u8 reserved; /* Reserved - must be zero */ u32 address; /* APIC physical address */ - u32 interrupt; /* Global system interrupt where INTI lines start */ + u32 global_irq_base; /* Global system interrupt where INTI lines start */ }; /* 2: Interrupt Override */ -struct madt_interrupt_override { - APIC_HEADER_DEF u8 bus; /* 0 - ISA */ - u8 source; /* Interrupt source (IRQ) */ - u32 interrupt; /* Global system interrupt */ - ACPI_MADT_IFLAGS}; +struct acpi_madt_interrupt_override { + struct acpi_subtable_header header; + u8 bus; /* 0 - ISA */ + u8 source_irq; /* Interrupt source (IRQ) */ + u32 global_irq; /* Global system interrupt */ + u16 inti_flags; +}; -/* 3: NMI Sources */ +/* 3: NMI Source */ -struct madt_nmi_source { - APIC_HEADER_DEF ACPI_MADT_IFLAGS u32 interrupt; /* Global system interrupt */ +struct acpi_madt_nmi_source { + struct acpi_subtable_header header; + u16 inti_flags; + u32 global_irq; /* Global system interrupt */ }; /* 4: Local APIC NMI */ -struct madt_local_apic_nmi { - APIC_HEADER_DEF u8 processor_id; /* ACPI processor id */ - ACPI_MADT_IFLAGS u8 lint; /* LINTn to which NMI is connected */ +struct acpi_madt_local_apic_nmi { + struct acpi_subtable_header header; + u8 processor_id; /* ACPI processor id */ + u16 inti_flags; + u8 lint; /* LINTn to which NMI is connected */ }; /* 5: Address Override */ -struct madt_address_override { - APIC_HEADER_DEF u16 reserved; /* Reserved, must be zero */ +struct acpi_madt_local_apic_override { + struct acpi_subtable_header header; + u16 reserved; /* Reserved, must be zero */ u64 address; /* APIC physical address */ }; /* 6: I/O Sapic */ -struct madt_io_sapic { - APIC_HEADER_DEF u8 io_sapic_id; /* I/O SAPIC ID */ +struct acpi_madt_io_sapic { + struct acpi_subtable_header header; + u8 id; /* I/O SAPIC ID */ u8 reserved; /* Reserved, must be zero */ - u32 interrupt_base; /* Glocal interrupt for SAPIC start */ + u32 global_irq_base; /* Global interrupt for SAPIC start */ u64 address; /* SAPIC physical address */ }; /* 7: Local Sapic */ -struct madt_local_sapic { - APIC_HEADER_DEF u8 processor_id; /* ACPI processor id */ - u8 local_sapic_id; /* SAPIC ID */ - u8 local_sapic_eid; /* SAPIC EID */ +struct acpi_madt_local_sapic { + struct acpi_subtable_header header; + u8 processor_id; /* ACPI processor id */ + u8 id; /* SAPIC ID */ + u8 eid; /* SAPIC EID */ u8 reserved[3]; /* Reserved, must be zero */ - ACPI_MADT_LFLAGS u32 processor_uID; /* Numeric UID - ACPI 3.0 */ - char processor_uIDstring[1]; /* String UID - ACPI 3.0 */ + u32 lapic_flags; + u32 uid; /* Numeric UID - ACPI 3.0 */ + char uid_string[1]; /* String UID - ACPI 3.0 */ }; /* 8: Platform Interrupt Source */ -struct madt_interrupt_source { - APIC_HEADER_DEF ACPI_MADT_IFLAGS u8 interrupt_type; /* 1=PMI, 2=INIT, 3=corrected */ - u8 processor_id; /* Processor ID */ - u8 processor_eid; /* Processor EID */ +struct acpi_madt_interrupt_source { + struct acpi_subtable_header header; + u16 inti_flags; + u8 type; /* 1=PMI, 2=INIT, 3=corrected */ + u8 id; /* Processor ID */ + u8 eid; /* Processor EID */ u8 io_sapic_vector; /* Vector value for PMI interrupts */ - u32 interrupt; /* Global system interrupt */ + u32 global_irq; /* Global system interrupt */ u32 flags; /* Interrupt Source Flags */ }; -#ifdef DUPLICATE_DEFINITION_WITH_LINUX_ACPI_H +/* Flags field above */ + +#define ACPI_MADT_CPEI_OVERRIDE (1) + +/* + * Common flags fields for MADT subtables + */ + +/* MADT Local APIC flags (lapic_flags) */ + +#define ACPI_MADT_ENABLED (1) /* 00: Processor is usable if set */ + +/* MADT MPS INTI flags (inti_flags) */ + +#define ACPI_MADT_POLARITY_MASK (3) /* 00-01: Polarity of APIC I/O input signals */ +#define ACPI_MADT_TRIGGER_MASK (3<<2) /* 02-03: Trigger mode of APIC input signals */ + +/* Values for MPS INTI flags */ + +#define ACPI_MADT_POLARITY_CONFORMS 0 +#define ACPI_MADT_POLARITY_ACTIVE_HIGH 1 +#define ACPI_MADT_POLARITY_RESERVED 2 +#define ACPI_MADT_POLARITY_ACTIVE_LOW 3 + +#define ACPI_MADT_TRIGGER_CONFORMS (0) +#define ACPI_MADT_TRIGGER_EDGE (1<<2) +#define ACPI_MADT_TRIGGER_RESERVED (2<<2) +#define ACPI_MADT_TRIGGER_LEVEL (3<<2) + /******************************************************************************* * * MCFG - PCI Memory Mapped Configuration table and sub-table @@ -406,17 +430,19 @@ struct madt_interrupt_source { ******************************************************************************/ struct acpi_table_mcfg { - ACPI_TABLE_HEADER_DEF u8 reserved[8]; + struct acpi_table_header header; /* Common ACPI table header */ + u8 reserved[8]; }; +/* Subtable */ + struct acpi_mcfg_allocation { - u64 base_address; /* Base address, processor-relative */ + u64 address; /* Base address, processor-relative */ u16 pci_segment; /* PCI segment group number */ u8 start_bus_number; /* Starting PCI Bus number */ u8 end_bus_number; /* Final PCI Bus number */ u32 reserved; }; -#endif /******************************************************************************* * @@ -424,8 +450,9 @@ struct acpi_mcfg_allocation { * ******************************************************************************/ -struct smart_battery_table { - ACPI_TABLE_HEADER_DEF u32 warning_level; +struct acpi_table_sbst { + struct acpi_table_header header; /* Common ACPI table header */ + u32 warning_level; u32 low_level; u32 critical_level; }; @@ -436,9 +463,10 @@ struct smart_battery_table { * ******************************************************************************/ -struct system_locality_info { - ACPI_TABLE_HEADER_DEF u64 locality_count; - u8 entry[1][1]; +struct acpi_table_slit { + struct acpi_table_header header; /* Common ACPI table header */ + u64 locality_count; + u8 entry[1]; /* Real size = localities^2 */ }; /******************************************************************************* @@ -448,7 +476,8 @@ struct system_locality_info { ******************************************************************************/ struct acpi_table_spcr { - ACPI_TABLE_HEADER_DEF u8 interface_type; /* 0=full 16550, 1=subset of 16550 */ + struct acpi_table_header header; /* Common ACPI table header */ + u8 interface_type; /* 0=full 16550, 1=subset of 16550 */ u8 reserved[3]; struct acpi_generic_address serial_port; u8 interrupt_type; @@ -459,7 +488,7 @@ struct acpi_table_spcr { u8 stop_bits; u8 flow_control; u8 terminal_type; - u8 reserved2; + u8 reserved1; u16 pci_device_id; u16 pci_vendor_id; u8 pci_bus; @@ -467,7 +496,7 @@ struct acpi_table_spcr { u8 pci_function; u32 pci_flags; u8 pci_segment; - u32 reserved3; + u32 reserved2; }; /******************************************************************************* @@ -477,12 +506,13 @@ struct acpi_table_spcr { ******************************************************************************/ struct acpi_table_spmi { - ACPI_TABLE_HEADER_DEF u8 reserved; + struct acpi_table_header header; /* Common ACPI table header */ + u8 reserved; u8 interface_type; u16 spec_revision; /* Version of IPMI */ u8 interrupt_type; u8 gpe_number; /* GPE assigned */ - u8 reserved2; + u8 reserved1; u8 pci_device_flag; u32 interrupt; struct acpi_generic_address ipmi_register; @@ -498,56 +528,61 @@ struct acpi_table_spmi { * ******************************************************************************/ -struct system_resource_affinity { - ACPI_TABLE_HEADER_DEF u32 reserved1; /* Must be value '1' */ - u64 reserved2; /* Reserved, must be zero */ +struct acpi_table_srat { + struct acpi_table_header header; /* Common ACPI table header */ + u32 table_revision; /* Must be value '1' */ + u64 reserved; /* Reserved, must be zero */ }; -/* SRAT common sub-table header */ - -#define SRAT_SUBTABLE_HEADER \ - u8 type; \ - u8 length; - -/* Values for Type above */ +/* Values for subtable type in struct acpi_subtable_header */ -#define SRAT_CPU_AFFINITY 0 -#define SRAT_MEMORY_AFFINITY 1 -#define SRAT_RESERVED 2 +enum acpi_srat_type { + ACPI_SRAT_TYPE_CPU_AFFINITY = 0, + ACPI_SRAT_TYPE_MEMORY_AFFINITY = 1, + ACPI_SRAT_TYPE_RESERVED = 2 +}; /* SRAT sub-tables */ -struct static_resource_alloc { - SRAT_SUBTABLE_HEADER u8 proximity_domain_lo; +struct acpi_srat_cpu_affinity { + struct acpi_subtable_header header; + u8 proximity_domain_lo; u8 apic_id; - - /* Flags (32 bits) */ - - u8 enabled:1; /* 00: Use affinity structure */ - u8:7; /* 01-07: Reserved, must be zero */ - u8 reserved3[3]; /* 08-31: Reserved, must be zero */ - + u32 flags; u8 local_sapic_eid; u8 proximity_domain_hi[3]; - u32 reserved4; /* Reserved, must be zero */ + u32 reserved; /* Reserved, must be zero */ }; -struct memory_affinity { - SRAT_SUBTABLE_HEADER u32 proximity_domain; - u16 reserved3; +/* Flags */ + +#define ACPI_SRAT_CPU_ENABLED (1) /* 00: Use affinity structure */ + +struct acpi_srat_mem_affinity { + struct acpi_subtable_header header; + u32 proximity_domain; + u16 reserved; /* Reserved, must be zero */ u64 base_address; - u64 address_length; - u32 reserved4; + u64 length; + u32 memory_type; /* See acpi_address_range_id */ + u32 flags; + u64 reserved1; /* Reserved, must be zero */ +}; + +/* Flags */ - /* Flags (32 bits) */ +#define ACPI_SRAT_MEM_ENABLED (1) /* 00: Use affinity structure */ +#define ACPI_SRAT_MEM_HOT_PLUGGABLE (1<<1) /* 01: Memory region is hot pluggable */ +#define ACPI_SRAT_MEM_NON_VOLATILE (1<<2) /* 02: Memory region is non-volatile */ - u8 enabled:1; /* 00: Use affinity structure */ - u8 hot_pluggable:1; /* 01: Memory region is hot pluggable */ - u8 non_volatile:1; /* 02: Memory is non-volatile */ - u8:5; /* 03-07: Reserved, must be zero */ - u8 reserved5[3]; /* 08-31: Reserved, must be zero */ +/* Memory types */ - u64 reserved6; /* Reserved, must be zero */ +enum acpi_address_range_id { + ACPI_ADDRESS_RANGE_MEMORY = 1, + ACPI_ADDRESS_RANGE_RESERVED = 2, + ACPI_ADDRESS_RANGE_ACPI = 3, + ACPI_ADDRESS_RANGE_NVS = 4, + ACPI_ADDRESS_RANGE_COUNT = 5 }; /******************************************************************************* @@ -557,7 +592,8 @@ struct memory_affinity { ******************************************************************************/ struct acpi_table_tcpa { - ACPI_TABLE_HEADER_DEF u16 reserved; + struct acpi_table_header header; /* Common ACPI table header */ + u16 reserved; u32 max_log_length; /* Maximum length for the event log area */ u64 log_address; /* Address of the event log area */ }; @@ -569,7 +605,8 @@ struct acpi_table_tcpa { ******************************************************************************/ struct acpi_table_wdrt { - ACPI_TABLE_HEADER_DEF u32 header_length; /* Watchdog Header Length */ + struct acpi_table_header header; /* Common ACPI table header */ + u32 header_length; /* Watchdog Header Length */ u8 pci_segment; /* PCI Segment number */ u8 pci_bus; /* PCI Bus number */ u8 pci_device; /* PCI Device number */ @@ -582,58 +619,9 @@ struct acpi_table_wdrt { u32 entries; /* Number of watchdog entries that follow */ }; -#if 0 /* Flags, will be converted to macros */ -u8 enabled:1; /* 00: Timer enabled */ -u8:6; /* 01-06: Reserved */ -u8 sleep_stop:1; /* 07: Timer stopped in sleep state */ -#endif - -/* Macros used to generate offsets to specific table fields */ - -#define ACPI_ASF0_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_asf_info,f) -#define ACPI_ASF1_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_asf_alert,f) -#define ACPI_ASF2_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_asf_remote,f) -#define ACPI_ASF3_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_asf_rmcp,f) -#define ACPI_ASF4_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_asf_address,f) -#define ACPI_BOOT_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_boot,f) -#define ACPI_CPEP_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_cpep,f) -#define ACPI_CPEP0_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_cpep_polling,f) -#define ACPI_DBGP_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_dbgp,f) -#define ACPI_ECDT_OFFSET(f) (u8) ACPI_OFFSET (struct ec_boot_resources,f) -#define ACPI_HPET_OFFSET(f) (u8) ACPI_OFFSET (struct hpet_table,f) -#define ACPI_MADT_OFFSET(f) (u8) ACPI_OFFSET (struct multiple_apic_table,f) -#define ACPI_MADT0_OFFSET(f) (u8) ACPI_OFFSET (struct madt_processor_apic,f) -#define ACPI_MADT1_OFFSET(f) (u8) ACPI_OFFSET (struct madt_io_apic,f) -#define ACPI_MADT2_OFFSET(f) (u8) ACPI_OFFSET (struct madt_interrupt_override,f) -#define ACPI_MADT3_OFFSET(f) (u8) ACPI_OFFSET (struct madt_nmi_source,f) -#define ACPI_MADT4_OFFSET(f) (u8) ACPI_OFFSET (struct madt_local_apic_nmi,f) -#define ACPI_MADT5_OFFSET(f) (u8) ACPI_OFFSET (struct madt_address_override,f) -#define ACPI_MADT6_OFFSET(f) (u8) ACPI_OFFSET (struct madt_io_sapic,f) -#define ACPI_MADT7_OFFSET(f) (u8) ACPI_OFFSET (struct madt_local_sapic,f) -#define ACPI_MADT8_OFFSET(f) (u8) ACPI_OFFSET (struct madt_interrupt_source,f) -#define ACPI_MADTH_OFFSET(f) (u8) ACPI_OFFSET (struct apic_header,f) -#define ACPI_MCFG_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_mcfg,f) -#define ACPI_MCFG0_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_mcfg_allocation,f) -#define ACPI_SBST_OFFSET(f) (u8) ACPI_OFFSET (struct smart_battery_table,f) -#define ACPI_SLIT_OFFSET(f) (u8) ACPI_OFFSET (struct system_locality_info,f) -#define ACPI_SPCR_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_spcr,f) -#define ACPI_SPMI_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_spmi,f) -#define ACPI_SRAT_OFFSET(f) (u8) ACPI_OFFSET (struct system_resource_affinity,f) -#define ACPI_SRAT0_OFFSET(f) (u8) ACPI_OFFSET (struct static_resource_alloc,f) -#define ACPI_SRAT1_OFFSET(f) (u8) ACPI_OFFSET (struct memory_affinity,f) -#define ACPI_TCPA_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_tcpa,f) -#define ACPI_WDRT_OFFSET(f) (u8) ACPI_OFFSET (struct acpi_table_wdrt,f) - -#define ACPI_HPET_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct hpet_table,f,o) -#define ACPI_SRAT0_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct static_resource_alloc,f,o) -#define ACPI_SRAT1_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct memory_affinity,f,o) -#define ACPI_MADT_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct multiple_apic_table,f,o) -#define ACPI_MADT0_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct madt_processor_apic,f,o) -#define ACPI_MADT2_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct madt_interrupt_override,f,o) -#define ACPI_MADT3_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct madt_nmi_source,f,o) -#define ACPI_MADT4_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct madt_local_apic_nmi,f,o) -#define ACPI_MADT7_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct madt_local_sapic,f,o) -#define ACPI_MADT8_FLAG_OFFSET(f,o) ACPI_FLAG_OFFSET (struct madt_interrupt_source,f,o) +/* Flags */ + +#define ACPI_WDRT_TIMER_ENABLED (1) /* 00: Timer enabled */ /* Reset to default packing */ diff --git a/include/acpi/actypes.h b/include/acpi/actypes.h index 64b603c..b0cdee6 100644 --- a/include/acpi/actypes.h +++ b/include/acpi/actypes.h @@ -191,7 +191,7 @@ typedef s32 acpi_native_int; typedef u64 acpi_table_ptr; typedef u32 acpi_io_address; -typedef u64 acpi_physical_address; +typedef u32 acpi_physical_address; #define ACPI_MAX_PTR ACPI_UINT32_MAX #define ACPI_SIZE_MAX ACPI_UINT32_MAX @@ -311,36 +311,6 @@ typedef acpi_native_uint acpi_size; * ******************************************************************************/ -/* - * Pointer overlays to avoid lots of typecasting for - * code that accepts both physical and logical pointers. - */ -union acpi_pointers { - acpi_physical_address physical; - void *logical; - acpi_table_ptr value; -}; - -struct acpi_pointer { - u32 pointer_type; - union acpi_pointers pointer; -}; - -/* pointer_types for above */ - -#define ACPI_PHYSICAL_POINTER 0x01 -#define ACPI_LOGICAL_POINTER 0x02 - -/* Processor mode */ - -#define ACPI_PHYSICAL_ADDRESSING 0x04 -#define ACPI_LOGICAL_ADDRESSING 0x08 -#define ACPI_MEMORY_MODE 0x0C - -#define ACPI_PHYSMODE_PHYSPTR ACPI_PHYSICAL_ADDRESSING | ACPI_PHYSICAL_POINTER -#define ACPI_LOGMODE_PHYSPTR ACPI_LOGICAL_ADDRESSING | ACPI_PHYSICAL_POINTER -#define ACPI_LOGMODE_LOGPTR ACPI_LOGICAL_ADDRESSING | ACPI_LOGICAL_POINTER - /* Logical defines and NULL */ #ifdef FALSE @@ -491,21 +461,6 @@ typedef u64 acpi_integer; #define ACPI_NOTIFY_POWER_FAULT (u8) 7 /* - * Table types. These values are passed to the table related APIs - */ -typedef u32 acpi_table_type; - -#define ACPI_TABLE_ID_RSDP (acpi_table_type) 0 -#define ACPI_TABLE_ID_DSDT (acpi_table_type) 1 -#define ACPI_TABLE_ID_FADT (acpi_table_type) 2 -#define ACPI_TABLE_ID_FACS (acpi_table_type) 3 -#define ACPI_TABLE_ID_PSDT (acpi_table_type) 4 -#define ACPI_TABLE_ID_SSDT (acpi_table_type) 5 -#define ACPI_TABLE_ID_XSDT (acpi_table_type) 6 -#define ACPI_TABLE_ID_MAX 6 -#define ACPI_NUM_TABLE_TYPES (ACPI_TABLE_ID_MAX+1) - -/* * Types associated with ACPI names and objects. The first group of * values (up to ACPI_TYPE_EXTERNAL_MAX) correspond to the definition * of the ACPI object_type() operator (See the ACPI Spec). Therefore, @@ -816,13 +771,6 @@ struct acpi_buffer { #define ACPI_SYS_MODES_MASK 0x0003 /* - * ACPI Table Info. One per ACPI table _type_ - */ -struct acpi_table_info { - u32 count; -}; - -/* * System info returned by acpi_get_system_info() */ struct acpi_system_info { @@ -833,8 +781,6 @@ struct acpi_system_info { u32 reserved2; u32 debug_level; u32 debug_layer; - u32 num_table_types; - struct acpi_table_info table_info[ACPI_TABLE_ID_MAX + 1]; }; /* -- cgit v0.10.2 From c5fc42ac4d4d6d3e3f619290b86890cb3725d2f8 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: misc fixes for new Table Manager: Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbinstal.c b/drivers/acpi/tables/tbinstal.c index 9076ca0..9e0b3ce 100644 --- a/drivers/acpi/tables/tbinstal.c +++ b/drivers/acpi/tables/tbinstal.c @@ -61,7 +61,7 @@ ACPI_MODULE_NAME("tbinstal") *****************************************************************************/ acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc) { - u8 checksum; + acpi_status status; ACPI_FUNCTION_TRACE(tb_verify_table); @@ -84,17 +84,9 @@ acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc) /* Always calculate checksum, ignore bad checksum if requested */ - checksum = acpi_tb_checksum(ACPI_CAST_PTR(void, table_desc->pointer), - table_desc->length); - -#if (ACPI_CHECKSUM_ABORT) - - if (checksum) { - return_ACPI_STATUS(AE_BAD_CHECKSUM); - } -#endif - - return_ACPI_STATUS(AE_OK); + status = + acpi_tb_verify_checksum(table_desc->pointer, table_desc->length); + return_ACPI_STATUS(status); } /******************************************************************************* @@ -188,7 +180,7 @@ acpi_status acpi_tb_resize_root_table_list(void) /* allow_resize flag is a parameter to acpi_initialize_tables */ - if (!(acpi_gbl_root_table_list.flags & ACPI_TABLE_FLAGS_ALLOW_RESIZE)) { + if (!(acpi_gbl_root_table_list.flags & ACPI_ROOT_ALLOW_RESIZE)) { ACPI_ERROR((AE_INFO, "Resize of Root Table Array is not allowed")); return_ACPI_STATUS(AE_SUPPORT); @@ -212,18 +204,14 @@ acpi_status acpi_tb_resize_root_table_list(void) acpi_gbl_root_table_list.size * sizeof(struct acpi_table_desc)); - if (acpi_gbl_root_table_list.flags & ACPI_TABLE_ORIGIN_MASK == - ACPI_TABLE_ORIGIN_ALLOCATED) { + if (acpi_gbl_root_table_list.flags & ACPI_ROOT_ORIGIN_ALLOCATED) { ACPI_FREE(acpi_gbl_root_table_list.tables); } } acpi_gbl_root_table_list.tables = tables; acpi_gbl_root_table_list.size += ACPI_ROOT_TABLE_SIZE_INCREMENT; - acpi_gbl_root_table_list.flags = (u8) (ACPI_TABLE_ORIGIN_ALLOCATED | - (acpi_gbl_root_table_list. - flags & - ~ACPI_TABLE_ORIGIN_MASK)); + acpi_gbl_root_table_list.flags |= (u8) ACPI_ROOT_ORIGIN_ALLOCATED; return_ACPI_STATUS(AE_OK); } @@ -348,8 +336,7 @@ void acpi_tb_terminate(void) * Delete the root table array if allocated locally. Array cannot be * mapped, so we don't need to check for that flag. */ - if ((acpi_gbl_root_table_list.flags & ACPI_TABLE_ORIGIN_MASK) == - ACPI_TABLE_ORIGIN_ALLOCATED) { + if (acpi_gbl_root_table_list.flags & ACPI_ROOT_ORIGIN_ALLOCATED) { ACPI_FREE(acpi_gbl_root_table_list.tables); } @@ -497,7 +484,7 @@ u8 acpi_tb_is_table_loaded(acpi_native_uint table_index) if (table_index < acpi_gbl_root_table_list.count) { is_loaded = (u8) (acpi_gbl_root_table_list.tables[table_index]. - flags & ACPI_TABLE_FLAGS_LOADED); + flags & ACPI_TABLE_IS_LOADED); } (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); @@ -524,10 +511,10 @@ void acpi_tb_set_table_loaded_flag(acpi_native_uint table_index, u8 is_loaded) if (table_index < acpi_gbl_root_table_list.count) { if (is_loaded) { acpi_gbl_root_table_list.tables[table_index].flags |= - ACPI_TABLE_FLAGS_LOADED; + ACPI_TABLE_IS_LOADED; } else { acpi_gbl_root_table_list.tables[table_index].flags &= - ~ACPI_TABLE_FLAGS_LOADED; + ~ACPI_TABLE_IS_LOADED; } } diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 3620ac5..2f4ab75 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -48,11 +48,52 @@ ACPI_MODULE_NAME("tbutils") /* Local prototypes */ -static void acpi_tb_parse_fadt(struct acpi_table_fadt *fadt, u8 flags); +static void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags); + +static void acpi_tb_convert_fadt(void); + +static void +acpi_tb_install_table(acpi_physical_address address, + u8 flags, char *signature, acpi_native_uint table_index); static void inline acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, - u8 bit_width, acpi_physical_address address); + u8 bit_width, u64 address); + +/* Table used for conversion of FADT to common format */ + +typedef struct acpi_fadt_conversion { + u8 target; + u8 source; + u8 length; + +} acpi_fadt_conversion; + +static struct acpi_fadt_conversion fadt_conversion_table[] = { + {ACPI_FADT_OFFSET(xpm1a_event_block), + ACPI_FADT_OFFSET(pm1a_event_block), + ACPI_FADT_OFFSET(pm1_event_length)}, + {ACPI_FADT_OFFSET(xpm1b_event_block), + ACPI_FADT_OFFSET(pm1b_event_block), + ACPI_FADT_OFFSET(pm1_event_length)}, + {ACPI_FADT_OFFSET(xpm1a_control_block), + ACPI_FADT_OFFSET(pm1a_control_block), + ACPI_FADT_OFFSET(pm1_control_length)}, + {ACPI_FADT_OFFSET(xpm1b_control_block), + ACPI_FADT_OFFSET(pm1b_control_block), + ACPI_FADT_OFFSET(pm1_control_length)}, + {ACPI_FADT_OFFSET(xpm2_control_block), + ACPI_FADT_OFFSET(pm2_control_block), + ACPI_FADT_OFFSET(pm2_control_length)}, + {ACPI_FADT_OFFSET(xpm_timer_block), ACPI_FADT_OFFSET(pm_timer_block), + ACPI_FADT_OFFSET(pm_timer_length)}, + {ACPI_FADT_OFFSET(xgpe0_block), ACPI_FADT_OFFSET(gpe0_block), + ACPI_FADT_OFFSET(gpe0_block_length)}, + {ACPI_FADT_OFFSET(xgpe1_block), ACPI_FADT_OFFSET(gpe1_block), + ACPI_FADT_OFFSET(gpe1_block_length)} +}; + +#define ACPI_FADT_CONVERSION_ENTRIES (sizeof (fadt_conversion_table) / sizeof (struct acpi_fadt_conversion)) /******************************************************************************* * @@ -63,7 +104,7 @@ acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, * * RETURN: None * - * DESCRIPTION: Print an ACPI table header + * DESCRIPTION: Print an ACPI table header. Special cases for FACS and RSDP. * ******************************************************************************/ @@ -72,12 +113,32 @@ acpi_tb_print_table_header(acpi_physical_address address, struct acpi_table_header *header) { - ACPI_INFO((AE_INFO, - "%4.4s @ 0x%p Length 0x%04X (v%3.3d %6.6s %8.8s 0x%08X %4.4s 0x%08X)", - header->signature, ACPI_CAST_PTR(void, address), - header->length, header->revision, header->oem_id, - header->oem_table_id, header->oem_revision, - header->asl_compiler_id, header->asl_compiler_revision)); + if (ACPI_COMPARE_NAME(header->signature, ACPI_SIG_FACS)) { + + /* FACS only has signature and length fields of common table header */ + + ACPI_INFO((AE_INFO, "%4.4s @ 0x%p/0x%04X", + header->signature, ACPI_CAST_PTR(void, address), + header->length)); + } else if (ACPI_COMPARE_NAME(header->signature, ACPI_SIG_RSDP)) { + + /* RSDP has no common fields */ + + ACPI_INFO((AE_INFO, "RSDP @ 0x%p/0x%04X (v%3.3d %6.6s)", + ACPI_CAST_PTR(void, address), + (((struct acpi_table_rsdp *)header)->revision > 0) ? + ((struct acpi_table_rsdp *)header)->length : 20, + ((struct acpi_table_rsdp *)header)->revision, + ((struct acpi_table_rsdp *)header)->oem_id)); + } else { + ACPI_INFO((AE_INFO, + "%4.4s @ 0x%p/0x%04X (v%3.3d %6.6s %8.8s 0x%08X %4.4s 0x%08X)", + header->signature, ACPI_CAST_PTR(void, address), + header->length, header->revision, header->oem_id, + header->oem_table_id, header->oem_revision, + header->asl_compiler_id, + header->asl_compiler_revision)); + } } /******************************************************************************* @@ -96,7 +157,7 @@ acpi_tb_print_table_header(acpi_physical_address address, static void inline acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, - u8 bit_width, acpi_physical_address address) + u8 bit_width, u64 address) { ACPI_STORE_ADDRESS(new_gas_struct->address, address); @@ -108,6 +169,45 @@ acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, /******************************************************************************* * + * FUNCTION: acpi_tb_validate_checksum + * + * PARAMETERS: Table - ACPI table to verify + * Length - Length of entire table + * + * RETURN: Status + * + * DESCRIPTION: Verifies that the table checksums to zero. Optionally returns + * exception on bad checksum. + * + ******************************************************************************/ + +acpi_status acpi_tb_verify_checksum(struct acpi_table_header *table, u32 length) +{ + u8 checksum; + + /* Compute the checksum on the table */ + + checksum = acpi_tb_checksum(ACPI_CAST_PTR(u8, table), length); + + /* Checksum ok? (should be zero) */ + + if (checksum) { + ACPI_WARNING((AE_INFO, + "Incorrect checksum in table [%4.4s] - %2.2X, should be %2.2X", + table->signature, table->checksum, + (u8) (table->checksum - checksum))); + +#if (ACPI_CHECKSUM_ABORT) + + return (AE_BAD_CHECKSUM); +#endif + } + + return (AE_OK); +} + +/******************************************************************************* + * * FUNCTION: acpi_tb_checksum * * PARAMETERS: Buffer - Pointer to memory region to be checked @@ -135,24 +235,38 @@ u8 acpi_tb_checksum(u8 * buffer, acpi_native_uint length) * * FUNCTION: acpi_tb_convert_fadt * - * PARAMETERS: Fadt - FADT table to be converted + * PARAMETERS: None, uses acpi_gbl_FADT * * RETURN: None * - * DESCRIPTION: Converts a BIOS supplied ACPI 1.0 FADT to a local - * ACPI 2.0 FADT. If the BIOS supplied a 2.0 FADT then it is simply - * copied to the local FADT. The ACPI CA software uses this - * local FADT. Thus a significant amount of special #ifdef - * type codeing is saved. + * DESCRIPTION: Converts all versions of the FADT to a common internal format. + * + * NOTE: acpi_gbl_FADT must be of size (struct acpi_table_fadt), and must contain + * a copy of the actual FADT. + * + * ACPICA will use the "X" fields of the FADT for all addresses. + * + * "X" fields are optional extensions to the original V1.0 fields. Even if + * they are present in the structure, they can be optionally not used by + * setting them to zero. Therefore, we must selectively expand V1.0 fields + * if the corresponding X field is zero. + * + * For ACPI 1.0 FADTs, all address fields are expanded to the corresponding + * "X" fields. + * + * For ACPI 2.0 FADTs, any "X" fields that are NULL are filled in by + * expanding the corresponding ACPI 1.0 field. * ******************************************************************************/ -void acpi_tb_convert_fadt(struct acpi_table_fadt *fadt) +static void acpi_tb_convert_fadt(void) { + u8 pm1_register_length; + struct acpi_generic_address *target; + acpi_native_uint i; + + /* Expand the FACS and DSDT addresses as necessary */ - /* - * Convert table pointers to 64-bit fields - */ if (!acpi_gbl_FADT.Xfacs) { acpi_gbl_FADT.Xfacs = (u64) acpi_gbl_FADT.facs; } @@ -162,62 +276,49 @@ void acpi_tb_convert_fadt(struct acpi_table_fadt *fadt) } /* - * Convert the V1.0 block addresses to V2.0 GAS structures + * Expand the V1.0 addresses to the "X" generic address structs, + * as necessary. */ - acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1a_event_block, - acpi_gbl_FADT.pm1_event_length, - (acpi_physical_address) acpi_gbl_FADT. - pm1a_event_block); - acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1b_event_block, - acpi_gbl_FADT.pm1_event_length, - (acpi_physical_address) acpi_gbl_FADT. - pm1b_event_block); - acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1a_control_block, - acpi_gbl_FADT.pm1_control_length, - (acpi_physical_address) acpi_gbl_FADT. - pm1a_control_block); - acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm1b_control_block, - acpi_gbl_FADT.pm1_control_length, - (acpi_physical_address) acpi_gbl_FADT. - pm1b_control_block); - acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm2_control_block, - acpi_gbl_FADT.pm2_control_length, - (acpi_physical_address) acpi_gbl_FADT. - pm2_control_block); - acpi_tb_init_generic_address(&acpi_gbl_FADT.xpm_timer_block, - acpi_gbl_FADT.pm_timer_length, - (acpi_physical_address) acpi_gbl_FADT. - pm_timer_block); - acpi_tb_init_generic_address(&acpi_gbl_FADT.xgpe0_block, 0, - (acpi_physical_address) acpi_gbl_FADT. - gpe0_block); - acpi_tb_init_generic_address(&acpi_gbl_FADT.xgpe1_block, 0, - (acpi_physical_address) acpi_gbl_FADT. - gpe1_block); + for (i = 0; i < ACPI_FADT_CONVERSION_ENTRIES; i++) { + target = + ACPI_ADD_PTR(struct acpi_generic_address, &acpi_gbl_FADT, + fadt_conversion_table[i].target); + + if (!target->address) { + acpi_tb_init_generic_address(target, + *ACPI_ADD_PTR(u8, + &acpi_gbl_FADT, + fadt_conversion_table + [i].length), + *ACPI_ADD_PTR(u64, + &acpi_gbl_FADT, + fadt_conversion_table + [i].source)); + } + } /* - * Create separate GAS structs for the PM1 Enable registers + * Calculate separate GAS structs for the PM1 Enable registers. + * These addresses do not appear (directly) in the FADT, so it is + * useful to calculate them once, here. */ + pm1_register_length = (u8) ACPI_DIV_2(acpi_gbl_FADT.pm1_event_length); + + /* PM1A is required */ + acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, - (u8) ACPI_DIV_2(acpi_gbl_FADT. - pm1_event_length), - (acpi_physical_address) - (acpi_gbl_FADT.xpm1a_event_block.address + - ACPI_DIV_2(acpi_gbl_FADT. - pm1_event_length))); + pm1_register_length, + (u64) (acpi_gbl_FADT.xpm1a_event_block. + address + pm1_register_length)); + + /* PM1B is optional; leave null if not present */ - /* - * PM1B is optional; leave null if not present - */ if (acpi_gbl_FADT.xpm1b_event_block.address) { acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, - (u8) ACPI_DIV_2(acpi_gbl_FADT. - pm1_event_length), - (acpi_physical_address) - (acpi_gbl_FADT.xpm1b_event_block. - address + - ACPI_DIV_2(acpi_gbl_FADT. - pm1_event_length))); + pm1_register_length, + (u64) (acpi_gbl_FADT. + xpm1b_event_block.address + + pm1_register_length)); } /* Global FADT is the new common V2.0 FADT */ @@ -227,84 +328,132 @@ void acpi_tb_convert_fadt(struct acpi_table_fadt *fadt) /******************************************************************************* * - * FUNCTION: acpi_tb_parse_fadt + * FUNCTION: acpi_tb_install_table * - * PARAMETERS: Fadt - Pointer to FADT table - * Flags - Flags + * PARAMETERS: Address - Physical address of DSDT or FACS + * Flags - Flags + * Signature - Table signature, NULL if no need to + * match + * table_index - Index into root table array * - * RETURN: none + * RETURN: None * - * DESCRIPTION: This function is called to initialise the FADT, DSDT and FACS - * tables (FADT contains the addresses of the DSDT and FACS) + * DESCRIPTION: Install an ACPI table into the global data structure. * ******************************************************************************/ -static void acpi_tb_parse_fadt(struct acpi_table_fadt *fadt, u8 flags) +static void +acpi_tb_install_table(acpi_physical_address address, + u8 flags, char *signature, acpi_native_uint table_index) { - acpi_physical_address dsdt_address = - (acpi_physical_address) fadt->Xdsdt; - acpi_physical_address facs_address = - (acpi_physical_address) fadt->Xfacs; struct acpi_table_header *table; - if (!dsdt_address) { - goto no_dsdt; + if (!address) { + ACPI_ERROR((AE_INFO, + "Null physical address for ACPI table [%s]", + signature)); + return; } - table = - acpi_os_map_memory(dsdt_address, sizeof(struct acpi_table_header)); + /* Map just the table header */ + + table = acpi_os_map_memory(address, sizeof(struct acpi_table_header)); if (!table) { - goto no_dsdt; + return; + } + + /* If a particular signature is expected, signature must match */ + + if (signature && !ACPI_COMPARE_NAME(table->signature, signature)) { + ACPI_ERROR((AE_INFO, + "Invalid signature 0x%X for ACPI table [%s]", + *ACPI_CAST_PTR(u32, table->signature), signature)); + goto unmap_and_exit; } - /* Initialize the DSDT table */ + /* Initialize the table entry */ + + acpi_gbl_root_table_list.tables[table_index].address = address; + acpi_gbl_root_table_list.tables[table_index].length = table->length; + acpi_gbl_root_table_list.tables[table_index].flags = flags; ACPI_MOVE_32_TO_32(& - (acpi_gbl_root_table_list. - tables[ACPI_TABLE_INDEX_DSDT].signature), - ACPI_SIG_DSDT); + (acpi_gbl_root_table_list.tables[table_index]. + signature), table->signature); - acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].address = - dsdt_address; - acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].length = - table->length; - acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].flags = flags; + acpi_tb_print_table_header(address, table); - acpi_tb_print_table_header(dsdt_address, table); + if (table_index == ACPI_TABLE_INDEX_DSDT) { - /* Global integer width is based upon revision of the DSDT */ + /* Global integer width is based upon revision of the DSDT */ - acpi_ut_set_integer_width(table->revision); + acpi_ut_set_integer_width(table->revision); + } + + unmap_and_exit: acpi_os_unmap_memory(table, sizeof(struct acpi_table_header)); +} - no_dsdt: - if (!facs_address) { - return; - } +/******************************************************************************* + * + * FUNCTION: acpi_tb_parse_fadt + * + * PARAMETERS: table_index - Index for the FADT + * Flags - Flags + * + * RETURN: None + * + * DESCRIPTION: Initialize the FADT, DSDT and FACS tables + * (FADT contains the addresses of the DSDT and FACS) + * + ******************************************************************************/ + +static void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) +{ + u32 length; + struct acpi_table_header *table; + + /* + * Special case for the FADT because of multiple versions and the fact + * that it contains pointers to both the DSDT and FACS tables. + * + * Get a local copy of the FADT and convert it to a common format + * Map entire FADT, assumed to be smaller than one page. + */ + length = acpi_gbl_root_table_list.tables[table_index].length; table = - acpi_os_map_memory(facs_address, sizeof(struct acpi_table_header)); + acpi_os_map_memory(acpi_gbl_root_table_list.tables[table_index]. + address, length); if (!table) { return; } - /* Initialize the FACS table */ + /* + * Validate the FADT checksum before we copy the table. Ignore + * checksum error as we want to try to get the DSDT and FACS. + */ + (void)acpi_tb_verify_checksum(table, length); - ACPI_MOVE_32_TO_32(& - (acpi_gbl_root_table_list. - tables[ACPI_TABLE_INDEX_FACS].signature), - ACPI_SIG_FACS); + /* Copy the entire FADT locally */ - acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_FACS].address = - facs_address; - acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_FACS].length = - table->length; - acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_FACS].flags = flags; + ACPI_MEMSET(&acpi_gbl_FADT, sizeof(struct acpi_table_fadt), 0); - ACPI_INFO((AE_INFO, "%4.4s @ 0x%p", - table->signature, ACPI_CAST_PTR(void, facs_address))); + ACPI_MEMCPY(&acpi_gbl_FADT, table, + ACPI_MIN(length, sizeof(struct acpi_table_fadt))); + acpi_os_unmap_memory(table, length); - acpi_os_unmap_memory(table, sizeof(struct acpi_table_header)); + /* Convert local FADT to the common internal format */ + + acpi_tb_convert_fadt(); + + /* Extract the DSDT and FACS tables from the FADT */ + + acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt, + flags, ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT); + + acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xfacs, + flags, ACPI_SIG_FACS, ACPI_TABLE_INDEX_FACS); } /******************************************************************************* @@ -325,20 +474,33 @@ static void acpi_tb_parse_fadt(struct acpi_table_fadt *fadt, u8 flags) * ******************************************************************************/ -acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags) +acpi_status +acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags) { + struct acpi_table_rsdp *rsdp; + acpi_native_uint table_entry_size; + acpi_native_uint i; + u32 table_count; struct acpi_table_header *table; acpi_physical_address address; u32 length; u8 *table_entry; - acpi_native_uint i; - acpi_native_uint pointer_size; - u32 table_count; - u8 checksum; acpi_status status; ACPI_FUNCTION_TRACE(tb_parse_root_table); + /* + * Map the entire RSDP and extract the address of the RSDT or XSDT + */ + rsdp = acpi_os_map_memory(rsdp_address, sizeof(struct acpi_table_rsdp)); + if (!rsdp) { + return_ACPI_STATUS(AE_NO_MEMORY); + } + + acpi_tb_print_table_header(rsdp_address, + ACPI_CAST_PTR(struct acpi_table_header, + rsdp)); + /* Differentiate between RSDT and XSDT root tables */ if (rsdp->revision > 1 && rsdp->xsdt_physical_address) { @@ -347,22 +509,30 @@ acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags) * XSDT if the revision is > 1 and the XSDT pointer is present, as per * the ACPI specification. */ - address = (acpi_native_uint) rsdp->xsdt_physical_address; - pointer_size = sizeof(u64); + address = (acpi_physical_address) rsdp->xsdt_physical_address; + table_entry_size = sizeof(u64); } else { /* Root table is an RSDT (32-bit physical addresses) */ - address = (acpi_native_uint) rsdp->rsdt_physical_address; - pointer_size = sizeof(u32); + address = (acpi_physical_address) rsdp->rsdt_physical_address; + table_entry_size = sizeof(u32); } - /* Map the table header to get the full table length */ + /* + * It is not possible to map more than one entry in some environments, + * so unmap the RSDP here before mapping other tables + */ + acpi_os_unmap_memory(rsdp, sizeof(struct acpi_table_rsdp)); + + /* Map the RSDT/XSDT table header to get the full table length */ table = acpi_os_map_memory(address, sizeof(struct acpi_table_header)); if (!table) { - return (AE_NO_MEMORY); + return_ACPI_STATUS(AE_NO_MEMORY); } + acpi_tb_print_table_header(address, table); + /* Get the length of the full table, verify length and map entire table */ length = table->length; @@ -371,48 +541,45 @@ acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags) if (length < sizeof(struct acpi_table_header)) { ACPI_ERROR((AE_INFO, "Invalid length 0x%X in RSDT/XSDT", length)); - return (AE_INVALID_TABLE_LENGTH); + return_ACPI_STATUS(AE_INVALID_TABLE_LENGTH); } table = acpi_os_map_memory(address, length); if (!table) { - return (AE_NO_MEMORY); + return_ACPI_STATUS(AE_NO_MEMORY); } /* Validate the root table checksum */ - checksum = acpi_tb_checksum(ACPI_CAST_PTR(u8, table), length); -#if (ACPI_CHECKSUM_ABORT) - - if (checksum) { + status = acpi_tb_verify_checksum(table, length); + if (ACPI_FAILURE(status)) { acpi_os_unmap_memory(table, length); - return (AE_BAD_CHECKSUM); + return_ACPI_STATUS(status); } -#endif - - acpi_tb_print_table_header(address, table); /* Calculate the number of tables described in the root table */ table_count = - (table->length - sizeof(struct acpi_table_header)) / pointer_size; - - /* Setup loop */ + (table->length - + sizeof(struct acpi_table_header)) / table_entry_size; + /* + * First two entries in the table array are reserved for the DSDT and FACS, + * which are not actually present in the RSDT/XSDT - they come from the FADT + */ table_entry = ACPI_CAST_PTR(u8, table) + sizeof(struct acpi_table_header); acpi_gbl_root_table_list.count = 2; /* - * Initialize the ACPI table entries - * First two entries in the table array are reserved for the DSDT and FACS + * Initialize the root table array from the RSDT/XSDT */ - for (i = 0; i < table_count; ++i, table_entry += pointer_size) { - - /* Ensure there is room for another table entry */ - + for (i = 0; i < table_count; i++) { if (acpi_gbl_root_table_list.count >= acpi_gbl_root_table_list.size) { + + /* There is no more room in the root table array, attempt resize */ + status = acpi_tb_resize_root_table_list(); if (ACPI_FAILURE(status)) { ACPI_WARNING((AE_INFO, @@ -425,20 +592,34 @@ acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags) } } - /* Get the physical address (32-bit for RSDT, 64-bit for XSDT) */ - - if (pointer_size == sizeof(u32)) { + /* + * Get the table physical address (32-bit for RSDT, 64-bit for XSDT) + */ + if ((table_entry_size == sizeof(u32)) || + (sizeof(acpi_physical_address) == sizeof(u32))) { + /* + * 32-bit platform, RSDT: Move 32-bit to 32-bit + * 32-bit platform, XSDT: Truncate 64-bit to 32-bit + * 64-bit platform, RSDT: Expand 32-bit to 64-bit + * + * Note: Addresses are 32-bit aligned in both RSDT and XSDT + */ acpi_gbl_root_table_list. tables[acpi_gbl_root_table_list.count].address = (acpi_physical_address) (*ACPI_CAST_PTR (u32, table_entry)); } else { - acpi_gbl_root_table_list. - tables[acpi_gbl_root_table_list.count].address = - (acpi_physical_address) (*ACPI_CAST_PTR - (u64, table_entry)); + /* + * 64-bit platform, XSDT: Move 64-bit to 64-bit + * + * Note: 64-bit addresses are only 32-bit aligned in the XSDT + */ + ACPI_MOVE_64_TO_64(&acpi_gbl_root_table_list. + tables[acpi_gbl_root_table_list. + count].address, table_entry); } + table_entry += table_entry_size; acpi_gbl_root_table_list.count++; } @@ -448,59 +629,20 @@ acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags) */ acpi_os_unmap_memory(table, length); - /* Initialize all tables other than the DSDT and FACS */ - + /* + * Complete the initialization of the root table array by examining + * the header of each table + */ for (i = 2; i < acpi_gbl_root_table_list.count; i++) { - address = acpi_gbl_root_table_list.tables[i].address; - length = sizeof(struct acpi_table_header); - - table = acpi_os_map_memory(address, length); - if (!table) { - continue; - } - - acpi_gbl_root_table_list.tables[i].length = table->length; - acpi_gbl_root_table_list.tables[i].flags = flags; - - ACPI_MOVE_32_TO_32(& - (acpi_gbl_root_table_list.tables[i]. - signature), table->signature); - - acpi_tb_print_table_header(address, table); - - /* - * Special case for the FADT because of multiple versions - - * get a local copy and convert to common format - */ - if (ACPI_COMPARE_NAME(table->signature, ACPI_SIG_FADT)) { - acpi_os_unmap_memory(table, length); - length = table->length; - - table = acpi_os_map_memory(address, length); - if (!table) { - continue; - } - - /* Copy the entire FADT locally */ - - ACPI_MEMCPY(&acpi_gbl_FADT, table, - ACPI_MIN(table->length, - sizeof(struct acpi_table_fadt))); + acpi_tb_install_table(acpi_gbl_root_table_list.tables[i]. + address, flags, NULL, i); - /* Small table means old revision, convert to new */ + /* Special case for FADT - get the DSDT and FACS */ - if (table->length < sizeof(struct acpi_table_fadt)) { - acpi_tb_convert_fadt(ACPI_CAST_PTR - (struct acpi_table_fadt, - table)); - } - - /* Unmap original FADT */ - - acpi_os_unmap_memory(table, length); - acpi_tb_parse_fadt(&acpi_gbl_FADT, flags); - } else { - acpi_os_unmap_memory(table, length); + if (ACPI_COMPARE_NAME + (&acpi_gbl_root_table_list.tables[i].signature, + ACPI_SIG_FADT)) { + acpi_tb_parse_fadt(i, flags); } } diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 77439fc..78ce542 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -82,9 +82,8 @@ acpi_status acpi_initialize_tables(struct acpi_table_desc *initial_table_array, u32 initial_table_count, u8 allow_resize) { - acpi_physical_address address; + acpi_physical_address rsdp_address; acpi_status status; - struct acpi_table_rsdp *rsdp; ACPI_FUNCTION_TRACE(acpi_initialize_tables); @@ -94,7 +93,7 @@ acpi_initialize_tables(struct acpi_table_desc *initial_table_array, */ if (!initial_table_array) { acpi_gbl_root_table_list.size = initial_table_count; - acpi_gbl_root_table_list.flags = ACPI_TABLE_FLAGS_ALLOW_RESIZE; + acpi_gbl_root_table_list.flags = ACPI_ROOT_ALLOW_RESIZE; status = acpi_tb_resize_root_table_list(); if (ACPI_FAILURE(status)) { @@ -103,37 +102,33 @@ acpi_initialize_tables(struct acpi_table_desc *initial_table_array, } else { /* Root Table Array has been statically allocated by the host */ + ACPI_MEMSET(initial_table_array, + initial_table_count * + sizeof(struct acpi_table_desc), 0); + acpi_gbl_root_table_list.tables = initial_table_array; acpi_gbl_root_table_list.size = initial_table_count; - acpi_gbl_root_table_list.flags = ACPI_TABLE_ORIGIN_UNKNOWN; + acpi_gbl_root_table_list.flags = ACPI_ROOT_ORIGIN_UNKNOWN; if (allow_resize) { - acpi_gbl_root_table_list.flags = - ACPI_TABLE_FLAGS_ALLOW_RESIZE; + acpi_gbl_root_table_list.flags |= + ACPI_ROOT_ALLOW_RESIZE; } } - /* Get the RSDP and map it */ + /* Get the address of the RSDP */ - address = acpi_os_get_root_pointer(); - if (!address) { + rsdp_address = acpi_os_get_root_pointer(); + if (!rsdp_address) { return_ACPI_STATUS(AE_NOT_FOUND); } - rsdp = acpi_os_map_memory(address, sizeof(struct acpi_table_rsdp)); - if (!rsdp) { - return_ACPI_STATUS(AE_NO_MEMORY); - } - - ACPI_INFO((AE_INFO, "%.8s @ 0x%p", - rsdp->signature, ACPI_CAST_PTR(void, address))); - /* * Get the root table (RSDT or XSDT) and extract all entries to the local * Root Table Array. This array contains the information of the RSDT/XSDT * in a common, more useable format. */ - status = acpi_tb_parse_root_table(rsdp, ACPI_TABLE_ORIGIN_MAPPED); - acpi_os_unmap_memory(rsdp, sizeof(struct acpi_table_rsdp)); + status = + acpi_tb_parse_root_table(rsdp_address, ACPI_TABLE_ORIGIN_MAPPED); return_ACPI_STATUS(status); } @@ -164,8 +159,7 @@ acpi_status acpi_reallocate_root_table(void) * Only reallocate the root table if the host provided a static buffer * for the table array in the call to acpi_initialize_tables. */ - if ((acpi_gbl_root_table_list.flags & ACPI_TABLE_ORIGIN_MASK) != - ACPI_TABLE_ORIGIN_UNKNOWN) { + if (acpi_gbl_root_table_list.flags & ACPI_ROOT_ORIGIN_ALLOCATED) { return_ACPI_STATUS(AE_SUPPORT); } @@ -185,7 +179,7 @@ acpi_status acpi_reallocate_root_table(void) acpi_gbl_root_table_list.size = acpi_gbl_root_table_list.count; acpi_gbl_root_table_list.tables = tables; acpi_gbl_root_table_list.flags = - ACPI_TABLE_ORIGIN_ALLOCATED | ACPI_TABLE_FLAGS_ALLOW_RESIZE; + ACPI_ROOT_ORIGIN_ALLOCATED | ACPI_ROOT_ALLOW_RESIZE; return_ACPI_STATUS(AE_OK); } @@ -247,6 +241,12 @@ acpi_get_table_header(char *signature, acpi_native_uint i; acpi_native_uint j; + /* Parameter validation */ + + if (!signature || !out_table_header) { + return (AE_BAD_PARAMETER); + } + /* * Walk the root table list */ @@ -267,7 +267,7 @@ acpi_get_table_header(char *signature, acpi_gbl_root_table_list.tables[i]. flags & ACPI_TABLE_ORIGIN_MASK); - if (!out_table_header) { + if (!(*out_table_header)) { return (AE_NO_MEMORY); } @@ -339,6 +339,12 @@ acpi_get_table(char *signature, acpi_native_uint j; acpi_status status; + /* Parameter validation */ + + if (!signature || !out_table) { + return (AE_BAD_PARAMETER); + } + /* * Walk the root table list */ @@ -387,6 +393,12 @@ acpi_get_table_by_index(acpi_native_uint table_index, ACPI_FUNCTION_TRACE(acpi_get_table_by_index); + /* Parameter validation */ + + if (!table) { + return_ACPI_STATUS(AE_BAD_PARAMETER); + } + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); /* Validate index */ diff --git a/drivers/acpi/utilities/utmisc.c b/drivers/acpi/utilities/utmisc.c index 47dcf82..4b03051 100644 --- a/drivers/acpi/utilities/utmisc.c +++ b/drivers/acpi/utilities/utmisc.c @@ -996,9 +996,13 @@ acpi_ut_info(char *module_name, u32 line_number, char *format, ...) { va_list args; - acpi_os_printf("ACPI (%s-%04d): ", module_name, line_number); + /* + * Removed module_name, line_number, and acpica version, not needed + * for info output + */ + acpi_os_printf("ACPI: "); va_start(args, format); acpi_os_vprintf(format, args); - acpi_os_printf(" [%X]\n", ACPI_CA_VERSION); + acpi_os_printf("\n"); } diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index 40f856c..1fea8ae 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20060823 +#define ACPI_CA_VERSION 0x20060828 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index 0f12fec..a870484 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -227,6 +227,16 @@ struct acpi_table_desc { u8 flags; }; +/* Flags for above */ + +#define ACPI_TABLE_ORIGIN_UNKNOWN (0) +#define ACPI_TABLE_ORIGIN_MAPPED (1) +#define ACPI_TABLE_ORIGIN_ALLOCATED (2) +#define ACPI_TABLE_ORIGIN_MASK (3) +#define ACPI_TABLE_IS_LOADED (4) + +/* One internal RSDT for table management */ + struct acpi_internal_rsdt { struct acpi_table_desc *tables; u32 count; @@ -234,14 +244,11 @@ struct acpi_internal_rsdt { u8 flags; }; -/* Flags for both structs above */ +/* Flags for above */ -#define ACPI_TABLE_ORIGIN_UNKNOWN (0) -#define ACPI_TABLE_ORIGIN_MAPPED (1) -#define ACPI_TABLE_ORIGIN_ALLOCATED (2) -#define ACPI_TABLE_ORIGIN_MASK (3) -#define ACPI_TABLE_FLAGS_LOADED (4) -#define ACPI_TABLE_FLAGS_ALLOW_RESIZE (8) +#define ACPI_ROOT_ORIGIN_UNKNOWN (0) /* ~ORIGIN_ALLOCATED */ +#define ACPI_ROOT_ORIGIN_ALLOCATED (1) +#define ACPI_ROOT_ALLOW_RESIZE (2) /* Predefined (fixed) table indexes */ diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 1737a2f..9183de1 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -94,9 +94,11 @@ acpi_tb_print_table_header(acpi_physical_address address, u8 acpi_tb_checksum(u8 * buffer, acpi_native_uint length); -void acpi_tb_convert_fadt(struct acpi_table_fadt *fadt); +acpi_status +acpi_tb_verify_checksum(struct acpi_table_header *table, u32 length); -acpi_status acpi_tb_parse_root_table(struct acpi_table_rsdp *rsdp, u8 flags); +acpi_status +acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags); void *acpi_tb_map(acpi_physical_address address, u32 length, u32 flags); diff --git a/include/acpi/actbl.h b/include/acpi/actbl.h index b455f54..c55939e 100644 --- a/include/acpi/actbl.h +++ b/include/acpi/actbl.h @@ -199,8 +199,8 @@ struct acpi_table_fadt { u32 pm1b_control_block; /* Port address of Power Mgt 1b Control Reg Blk */ u32 pm2_control_block; /* Port address of Power Mgt 2 Control Reg Blk */ u32 pm_timer_block; /* Port address of Power Mgt Timer Ctrl Reg Blk */ - u32 gpe0_block; /* Port addr of General Purpose acpi_event 0 Reg Blk */ - u32 gpe1_block; /* Port addr of General Purpose acpi_event 1 Reg Blk */ + u32 gpe0_block; /* Port addr of General Purpose Event 0 Reg Blk */ + u32 gpe1_block; /* Port addr of General Purpose Event 1 Reg Blk */ u8 pm1_event_length; /* Byte Length of ports at pm1_x_evt_blk */ u8 pm1_control_length; /* Byte Length of ports at pm1_x_cnt_blk */ u8 pm2_control_length; /* Byte Length of ports at pm2_cnt_blk */ @@ -226,14 +226,14 @@ struct acpi_table_fadt { u8 reserved4[3]; /* These three bytes must be zero */ u64 Xfacs; /* 64-bit physical address of FACS */ u64 Xdsdt; /* 64-bit physical address of DSDT */ - struct acpi_generic_address xpm1a_event_block; /* Extended Power Mgt 1a acpi_event Reg Blk address */ - struct acpi_generic_address xpm1b_event_block; /* Extended Power Mgt 1b acpi_event Reg Blk address */ + struct acpi_generic_address xpm1a_event_block; /* Extended Power Mgt 1a Event Reg Blk address */ + struct acpi_generic_address xpm1b_event_block; /* Extended Power Mgt 1b Event Reg Blk address */ struct acpi_generic_address xpm1a_control_block; /* Extended Power Mgt 1a Control Reg Blk address */ struct acpi_generic_address xpm1b_control_block; /* Extended Power Mgt 1b Control Reg Blk address */ struct acpi_generic_address xpm2_control_block; /* Extended Power Mgt 2 Control Reg Blk address */ struct acpi_generic_address xpm_timer_block; /* Extended Power Mgt Timer Ctrl Reg Blk address */ - struct acpi_generic_address xgpe0_block; /* Extended General Purpose acpi_event 0 Reg Blk address */ - struct acpi_generic_address xgpe1_block; /* Extended General Purpose acpi_event 1 Reg Blk address */ + struct acpi_generic_address xgpe0_block; /* Extended General Purpose Event 0 Reg Blk address */ + struct acpi_generic_address xgpe1_block; /* Extended General Purpose Event 1 Reg Blk address */ }; /* FADT flags */ -- cgit v0.10.2 From 8f34890dce60f7df6dd23a0d04977c6572adaab8 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Update comments for individual table fields comments only Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/actbl.h b/include/acpi/actbl.h index c55939e..aed49a5 100644 --- a/include/acpi/actbl.h +++ b/include/acpi/actbl.h @@ -56,7 +56,7 @@ #define ACPI_SIG_RSDT "RSDT" /* Root System Description Table */ #define ACPI_SIG_XSDT "XSDT" /* Extended System Description Table */ #define ACPI_SIG_SSDT "SSDT" /* Secondary System Description Table */ -#define ACPI_RSDP_NAME "RSDP" +#define ACPI_RSDP_NAME "RSDP" /* Short name for RSDP, not signature */ /* * All tables and structures must be byte-packed to match the ACPI @@ -185,55 +185,55 @@ struct acpi_table_fadt { struct acpi_table_header header; /* Common ACPI table header */ u32 facs; /* 32-bit physical address of FACS */ u32 dsdt; /* 32-bit physical address of DSDT */ - u8 model; /* System Interrupt Model (ACPI 1.0) not used in ACPI 2.0+ */ + u8 model; /* System Interrupt Model (ACPI 1.0) - not used in ACPI 2.0+ */ u8 preferred_profile; /* Conveys preferred power management profile to OSPM. */ u16 sci_interrupt; /* System vector of SCI interrupt */ - u32 smi_command; /* Port address of SMI command port */ + u32 smi_command; /* 32-bit Port address of SMI command port */ u8 acpi_enable; /* Value to write to smi_cmd to enable ACPI */ u8 acpi_disable; /* Value to write to smi_cmd to disable ACPI */ u8 S4bios_request; /* Value to write to SMI CMD to enter S4BIOS state */ u8 pstate_control; /* Processor performance state control */ - u32 pm1a_event_block; /* Port address of Power Mgt 1a Event Reg Blk */ - u32 pm1b_event_block; /* Port address of Power Mgt 1b Event Reg Blk */ - u32 pm1a_control_block; /* Port address of Power Mgt 1a Control Reg Blk */ - u32 pm1b_control_block; /* Port address of Power Mgt 1b Control Reg Blk */ - u32 pm2_control_block; /* Port address of Power Mgt 2 Control Reg Blk */ - u32 pm_timer_block; /* Port address of Power Mgt Timer Ctrl Reg Blk */ - u32 gpe0_block; /* Port addr of General Purpose Event 0 Reg Blk */ - u32 gpe1_block; /* Port addr of General Purpose Event 1 Reg Blk */ - u8 pm1_event_length; /* Byte Length of ports at pm1_x_evt_blk */ - u8 pm1_control_length; /* Byte Length of ports at pm1_x_cnt_blk */ - u8 pm2_control_length; /* Byte Length of ports at pm2_cnt_blk */ - u8 pm_timer_length; /* Byte Length of ports at pm_tmr_blk */ - u8 gpe0_block_length; /* Byte Length of ports at gpe0_blk */ - u8 gpe1_block_length; /* Byte Length of ports at gpe1_blk */ - u8 gpe1_base; /* Offset in gpe model where gpe1 events start */ - u8 cst_control; /* Support for the _CST object and C States change notification. */ + u32 pm1a_event_block; /* 32-bit Port address of Power Mgt 1a Event Reg Blk */ + u32 pm1b_event_block; /* 32-bit Port address of Power Mgt 1b Event Reg Blk */ + u32 pm1a_control_block; /* 32-bit Port address of Power Mgt 1a Control Reg Blk */ + u32 pm1b_control_block; /* 32-bit Port address of Power Mgt 1b Control Reg Blk */ + u32 pm2_control_block; /* 32-bit Port address of Power Mgt 2 Control Reg Blk */ + u32 pm_timer_block; /* 32-bit Port address of Power Mgt Timer Ctrl Reg Blk */ + u32 gpe0_block; /* 32-bit Port address of General Purpose Event 0 Reg Blk */ + u32 gpe1_block; /* 32-bit Port address of General Purpose Event 1 Reg Blk */ + u8 pm1_event_length; /* Byte Length of ports at pm1x_event_block */ + u8 pm1_control_length; /* Byte Length of ports at pm1x_control_block */ + u8 pm2_control_length; /* Byte Length of ports at pm2_control_block */ + u8 pm_timer_length; /* Byte Length of ports at pm_timer_block */ + u8 gpe0_block_length; /* Byte Length of ports at gpe0_block */ + u8 gpe1_block_length; /* Byte Length of ports at gpe1_block */ + u8 gpe1_base; /* Offset in GPE number space where GPE1 events start */ + u8 cst_control; /* Support for the _CST object and C States change notification */ u16 C2latency; /* Worst case HW latency to enter/exit C2 state */ u16 C3latency; /* Worst case HW latency to enter/exit C3 state */ u16 flush_size; /* Processor's memory cache line width, in bytes */ u16 flush_stride; /* Number of flush strides that need to be read */ - u8 duty_offset; /* Processor's duty cycle index in processor's P_CNT reg */ - u8 duty_width; /* Processor's duty cycle value bit width in P_CNT register. */ + u8 duty_offset; /* Processor duty cycle index in processor's P_CNT reg */ + u8 duty_width; /* Processor duty cycle value bit width in P_CNT register. */ u8 day_alarm; /* Index to day-of-month alarm in RTC CMOS RAM */ u8 month_alarm; /* Index to month-of-year alarm in RTC CMOS RAM */ u8 century; /* Index to century in RTC CMOS RAM */ u16 boot_flags; /* IA-PC Boot Architecture Flags. See Table 5-10 for description */ u8 reserved; /* Reserved, must be zero */ - u32 flags; /* Miscellaneous flag bits */ - struct acpi_generic_address reset_register; /* Reset register address in GAS format */ + u32 flags; /* Miscellaneous flag bits (see below for individual flags) */ + struct acpi_generic_address reset_register; /* 64-bit address of the Reset register */ u8 reset_value; /* Value to write to the reset_register port to reset the system */ - u8 reserved4[3]; /* These three bytes must be zero */ + u8 reserved4[3]; /* Reserved, must be zero */ u64 Xfacs; /* 64-bit physical address of FACS */ u64 Xdsdt; /* 64-bit physical address of DSDT */ - struct acpi_generic_address xpm1a_event_block; /* Extended Power Mgt 1a Event Reg Blk address */ - struct acpi_generic_address xpm1b_event_block; /* Extended Power Mgt 1b Event Reg Blk address */ - struct acpi_generic_address xpm1a_control_block; /* Extended Power Mgt 1a Control Reg Blk address */ - struct acpi_generic_address xpm1b_control_block; /* Extended Power Mgt 1b Control Reg Blk address */ - struct acpi_generic_address xpm2_control_block; /* Extended Power Mgt 2 Control Reg Blk address */ - struct acpi_generic_address xpm_timer_block; /* Extended Power Mgt Timer Ctrl Reg Blk address */ - struct acpi_generic_address xgpe0_block; /* Extended General Purpose Event 0 Reg Blk address */ - struct acpi_generic_address xgpe1_block; /* Extended General Purpose Event 1 Reg Blk address */ + struct acpi_generic_address xpm1a_event_block; /* 64-bit Extended Power Mgt 1a Event Reg Blk address */ + struct acpi_generic_address xpm1b_event_block; /* 64-bit Extended Power Mgt 1b Event Reg Blk address */ + struct acpi_generic_address xpm1a_control_block; /* 64-bit Extended Power Mgt 1a Control Reg Blk address */ + struct acpi_generic_address xpm1b_control_block; /* 64-bit Extended Power Mgt 1b Control Reg Blk address */ + struct acpi_generic_address xpm2_control_block; /* 64-bit Extended Power Mgt 2 Control Reg Blk address */ + struct acpi_generic_address xpm_timer_block; /* 64-bit Extended Power Mgt Timer Ctrl Reg Blk address */ + struct acpi_generic_address xgpe0_block; /* 64-bit Extended General Purpose Event 0 Reg Blk address */ + struct acpi_generic_address xgpe1_block; /* 64-bit Extended General Purpose Event 1 Reg Blk address */ }; /* FADT flags */ -- cgit v0.10.2 From 4bf273939c99fae5bae399f51c417a552d74b97f Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Fix for FADT conversion in 64-bit mode Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 2f4ab75..77c7e87 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -131,6 +131,8 @@ acpi_tb_print_table_header(acpi_physical_address address, ((struct acpi_table_rsdp *)header)->revision, ((struct acpi_table_rsdp *)header)->oem_id)); } else { + /* Standard ACPI table with full common header */ + ACPI_INFO((AE_INFO, "%4.4s @ 0x%p/0x%04X (v%3.3d %6.6s %8.8s 0x%08X %4.4s 0x%08X)", header->signature, ACPI_CAST_PTR(void, address), @@ -160,7 +162,7 @@ acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, u8 bit_width, u64 address) { - ACPI_STORE_ADDRESS(new_gas_struct->address, address); + ACPI_MOVE_64_TO_64(&new_gas_struct->address, &address); new_gas_struct->space_id = ACPI_ADR_SPACE_SYSTEM_IO; new_gas_struct->bit_width = bit_width; new_gas_struct->bit_offset = 0; @@ -284,13 +286,15 @@ static void acpi_tb_convert_fadt(void) ACPI_ADD_PTR(struct acpi_generic_address, &acpi_gbl_FADT, fadt_conversion_table[i].target); + /* Expand only if the X target is null */ + if (!target->address) { acpi_tb_init_generic_address(target, *ACPI_ADD_PTR(u8, &acpi_gbl_FADT, fadt_conversion_table [i].length), - *ACPI_ADD_PTR(u64, + *ACPI_ADD_PTR(u32, &acpi_gbl_FADT, fadt_conversion_table [i].source)); @@ -301,6 +305,10 @@ static void acpi_tb_convert_fadt(void) * Calculate separate GAS structs for the PM1 Enable registers. * These addresses do not appear (directly) in the FADT, so it is * useful to calculate them once, here. + * + * The PM event blocks are split into two register blocks, first is the + * PM Status Register block, followed immediately by the PM Enable Register + * block. Each is of length (pm1_event_length/2) */ pm1_register_length = (u8) ACPI_DIV_2(acpi_gbl_FADT.pm1_event_length); @@ -308,17 +316,16 @@ static void acpi_tb_convert_fadt(void) acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, pm1_register_length, - (u64) (acpi_gbl_FADT.xpm1a_event_block. - address + pm1_register_length)); + (acpi_gbl_FADT.xpm1a_event_block.address + + pm1_register_length)); /* PM1B is optional; leave null if not present */ if (acpi_gbl_FADT.xpm1b_event_block.address) { acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, pm1_register_length, - (u64) (acpi_gbl_FADT. - xpm1b_event_block.address + - pm1_register_length)); + (acpi_gbl_FADT.xpm1b_event_block. + address + pm1_register_length)); } /* Global FADT is the new common V2.0 FADT */ -- cgit v0.10.2 From a4bbb810dedaecf74d54b16b6dd3c33e95e1024c Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Lint changes Lint changes Move RSDT/XSDT pointer extraction to separate function Warning on 32-bit platforms if XSDT pointers use more than 32 bits. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 77c7e87..8e44f83 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -60,6 +60,10 @@ static void inline acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, u8 bit_width, u64 address); +static acpi_physical_address +acpi_tb_get_root_table_entry(u8 * table_entry, + acpi_native_uint table_entry_size); + /* Table used for conversion of FADT to common format */ typedef struct acpi_fadt_conversion { @@ -126,10 +130,14 @@ acpi_tb_print_table_header(acpi_physical_address address, ACPI_INFO((AE_INFO, "RSDP @ 0x%p/0x%04X (v%3.3d %6.6s)", ACPI_CAST_PTR(void, address), - (((struct acpi_table_rsdp *)header)->revision > 0) ? - ((struct acpi_table_rsdp *)header)->length : 20, - ((struct acpi_table_rsdp *)header)->revision, - ((struct acpi_table_rsdp *)header)->oem_id)); + (ACPI_CAST_PTR(struct acpi_table_rsdp, header)-> + revision > + 0) ? ACPI_CAST_PTR(struct acpi_table_rsdp, + header)->length : 20, + ACPI_CAST_PTR(struct acpi_table_rsdp, + header)->revision, + ACPI_CAST_PTR(struct acpi_table_rsdp, + header)->oem_id)); } else { /* Standard ACPI table with full common header */ @@ -278,8 +286,8 @@ static void acpi_tb_convert_fadt(void) } /* - * Expand the V1.0 addresses to the "X" generic address structs, - * as necessary. + * Expand the 32-bit V1.0 addresses to the 64-bit "X" generic address + * structures as necessary. */ for (i = 0; i < ACPI_FADT_CONVERSION_ENTRIES; i++) { target = @@ -294,10 +302,11 @@ static void acpi_tb_convert_fadt(void) &acpi_gbl_FADT, fadt_conversion_table [i].length), - *ACPI_ADD_PTR(u32, - &acpi_gbl_FADT, - fadt_conversion_table - [i].source)); + (u64) * ACPI_ADD_PTR(u32, + &acpi_gbl_FADT, + fadt_conversion_table + [i]. + source)); } } @@ -444,7 +453,7 @@ static void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) /* Copy the entire FADT locally */ - ACPI_MEMSET(&acpi_gbl_FADT, sizeof(struct acpi_table_fadt), 0); + ACPI_MEMSET(&acpi_gbl_FADT, 0, sizeof(struct acpi_table_fadt)); ACPI_MEMCPY(&acpi_gbl_FADT, table, ACPI_MIN(length, sizeof(struct acpi_table_fadt))); @@ -465,6 +474,61 @@ static void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) /******************************************************************************* * + * FUNCTION: acpi_tb_get_root_table_entry + * + * PARAMETERS: table_entry - Pointer to the RSDT/XSDT table entry + * table_entry_size - sizeof 32 or 64 (RSDT or XSDT) + * + * RETURN: Physical address extracted from the root table + * + * DESCRIPTION: Get one root table entry. Handles 32-bit and 64-bit cases on + * both 32-bit and 64-bit platforms + * + * NOTE: acpi_physical_address is 32-bit on 32-bit platforms, 64-bit on + * 64-bit platforms. + * + ******************************************************************************/ + +static acpi_physical_address +acpi_tb_get_root_table_entry(u8 * table_entry, + acpi_native_uint table_entry_size) +{ + u64 address64; + + /* + * Get the table physical address (32-bit for RSDT, 64-bit for XSDT): + * Note: Addresses are 32-bit aligned (not 64) in both RSDT and XSDT + */ + if (table_entry_size == sizeof(u32)) { + /* + * 32-bit platform, RSDT: Return 32-bit table entry + * 64-bit platform, RSDT: Expand 32-bit to 64-bit and return + */ + return ((acpi_physical_address) + (*ACPI_CAST_PTR(u32, table_entry))); + } else { + /* + * 32-bit platform, XSDT: Truncate 64-bit to 32-bit and return + * 64-bit platform, XSDT: Move (unaligned) 64-bit to local, return 64-bit + */ + ACPI_MOVE_64_TO_64(&address64, table_entry); + +#if ACPI_MACHINE_WIDTH == 32 + if (address64 > ACPI_UINT32_MAX) { + + /* Will truncate 64-bit address to 32 bits */ + + ACPI_WARNING((AE_INFO, + "64-bit Physical Address in XSDT is too large (%8.8X%8.8X), truncating", + ACPI_FORMAT_UINT64(address64))); + } +#endif + return ((acpi_physical_address) (address64)); + } +} + +/******************************************************************************* + * * FUNCTION: acpi_tb_parse_root_table * * PARAMETERS: Rsdp - Pointer to the RSDP @@ -567,8 +631,8 @@ acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags) /* Calculate the number of tables described in the root table */ table_count = - (table->length - - sizeof(struct acpi_table_header)) / table_entry_size; + (u32) ((table->length - + sizeof(struct acpi_table_header)) / table_entry_size); /* * First two entries in the table array are reserved for the DSDT and FACS, @@ -599,32 +663,11 @@ acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags) } } - /* - * Get the table physical address (32-bit for RSDT, 64-bit for XSDT) - */ - if ((table_entry_size == sizeof(u32)) || - (sizeof(acpi_physical_address) == sizeof(u32))) { - /* - * 32-bit platform, RSDT: Move 32-bit to 32-bit - * 32-bit platform, XSDT: Truncate 64-bit to 32-bit - * 64-bit platform, RSDT: Expand 32-bit to 64-bit - * - * Note: Addresses are 32-bit aligned in both RSDT and XSDT - */ - acpi_gbl_root_table_list. - tables[acpi_gbl_root_table_list.count].address = - (acpi_physical_address) (*ACPI_CAST_PTR - (u32, table_entry)); - } else { - /* - * 64-bit platform, XSDT: Move 64-bit to 64-bit - * - * Note: 64-bit addresses are only 32-bit aligned in the XSDT - */ - ACPI_MOVE_64_TO_64(&acpi_gbl_root_table_list. - tables[acpi_gbl_root_table_list. - count].address, table_entry); - } + /* Get the table physical address (32-bit for RSDT, 64-bit for XSDT) */ + + acpi_gbl_root_table_list.tables[acpi_gbl_root_table_list.count]. + address = + acpi_tb_get_root_table_entry(table_entry, table_entry_size); table_entry += table_entry_size; acpi_gbl_root_table_list.count++; diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 78ce542..13e8d66 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -102,9 +102,9 @@ acpi_initialize_tables(struct acpi_table_desc *initial_table_array, } else { /* Root Table Array has been statically allocated by the host */ - ACPI_MEMSET(initial_table_array, + ACPI_MEMSET(initial_table_array, 0, initial_table_count * - sizeof(struct acpi_table_desc), 0); + sizeof(struct acpi_table_desc)); acpi_gbl_root_table_list.tables = initial_table_array; acpi_gbl_root_table_list.size = initial_table_count; -- cgit v0.10.2 From ad71860a17ba33eb0e673e9e2cf5ba0d8e3e3fdd Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: minimal patch to integrate new tables into Linux Signed-off-by: Len Brown diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index cbcb2c2..9adabc4 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -716,33 +716,26 @@ static int __init acpi_parse_fadt(unsigned long phys, unsigned long size) printk(KERN_WARNING PREFIX "Unable to map FADT\n"); return 0; } - /* initialize sci_int early for INT_SRC_OVR MADT parsing */ - acpi_fadt.sci_int = fadt->sci_int; - - /* initialize rev and apic_phys_dest_mode for x86_64 genapic */ - acpi_fadt.revision = fadt->revision; - acpi_fadt.force_apic_physical_destination_mode = - fadt->force_apic_physical_destination_mode; #ifdef CONFIG_X86_PM_TIMER /* detect the location of the ACPI PM Timer */ - if (fadt->revision >= FADT2_REVISION_ID) { + if (fadt->header.revision >= FADT2_REVISION_ID) { /* FADT rev. 2 */ - if (fadt->xpm_tmr_blk.address_space_id != + if (fadt->xpm_timer_block.space_id != ACPI_ADR_SPACE_SYSTEM_IO) return 0; - pmtmr_ioport = fadt->xpm_tmr_blk.address; + pmtmr_ioport = fadt->xpm_timer_block.address; /* * "X" fields are optional extensions to the original V1.0 * fields, so we must selectively expand V1.0 fields if the * corresponding X field is zero. */ if (!pmtmr_ioport) - pmtmr_ioport = fadt->V1_pm_tmr_blk; + pmtmr_ioport = fadt->pm_timer_block; } else { /* FADT rev. 1 */ - pmtmr_ioport = fadt->V1_pm_tmr_blk; + pmtmr_ioport = fadt->pm_timer_block; } if (pmtmr_ioport) printk(KERN_INFO PREFIX "PM-Timer IO Port: %#x\n", diff --git a/arch/ia64/kernel/acpi.c b/arch/ia64/kernel/acpi.c index ef2fe47..aa6f967 100644 --- a/arch/ia64/kernel/acpi.c +++ b/arch/ia64/kernel/acpi.c @@ -76,7 +76,7 @@ const char *acpi_get_sysname(void) { #ifdef CONFIG_IA64_GENERIC unsigned long rsdp_phys; - struct acpi20_table_rsdp *rsdp; + struct acpi_table_rsdp *rsdp; struct acpi_table_xsdt *xsdt; struct acpi_table_header *hdr; @@ -87,8 +87,8 @@ const char *acpi_get_sysname(void) return "dig"; } - rsdp = (struct acpi20_table_rsdp *)__va(rsdp_phys); - if (strncmp(rsdp->signature, RSDP_SIG, sizeof(RSDP_SIG) - 1)) { + rsdp = (struct acpi_table_rsdp *)__va(rsdp_phys); + if (strncmp(rsdp->signature, ACPI_SIG_RSDP, sizeof(ACPI_SIG_RSDP) - 1)) { printk(KERN_ERR "ACPI 2.0 RSDP signature incorrect, default to \"dig\"\n"); return "dig"; @@ -96,7 +96,7 @@ const char *acpi_get_sysname(void) xsdt = (struct acpi_table_xsdt *)__va(rsdp->xsdt_address); hdr = &xsdt->header; - if (strncmp(hdr->signature, XSDT_SIG, sizeof(XSDT_SIG) - 1)) { + if (strncmp(hdr->signature, ACPI_SIG_XSDT, sizeof(ACPI_SIG_XSDT) - 1)) { printk(KERN_ERR "ACPI 2.0 XSDT signature incorrect, default to \"dig\"\n"); return "dig"; diff --git a/arch/ia64/sn/kernel/io_common.c b/arch/ia64/sn/kernel/io_common.c index d4dd8f4..65979f1 100644 --- a/arch/ia64/sn/kernel/io_common.c +++ b/arch/ia64/sn/kernel/io_common.c @@ -25,7 +25,6 @@ #include "xtalk/xwidgetdev.h" #include #include -#include extern void sn_init_cpei_timer(void); extern void register_sn_procfs(void); @@ -37,7 +36,6 @@ extern void sn_legacy_pci_window_fixup(struct pci_controller *, u64, u64); extern void sn_io_acpi_init(void); extern void sn_io_init(void); - static struct list_head sn_sysdata_list; /* sysdata list struct */ @@ -50,6 +48,15 @@ int sn_ioif_inited; /* SN I/O infrastructure initialized? */ struct sn_pcibus_provider *sn_pci_provider[PCIIO_ASIC_MAX_TYPES]; /* indexed by asic type */ +int sn_acpi_base_support() +{ + struct acpi_table_header *header; + (void)acpi_get_table_by_index(ACPI_TABLE_INDEX_DSDT, &header); + if (header && header->oem_revision >= 0x20101) + return 1; + return 0; +} + /* * Hooks and struct for unsupported pci providers */ @@ -286,7 +293,7 @@ void sn_pci_fixup_slot(struct pci_dev *dev) list_add_tail(&pcidev_info->pdi_list, &(SN_PLATFORM_DATA(dev->bus)->pcidev_info)); - if (SN_ACPI_BASE_SUPPORT()) + if (sn_acpi_base_support()) sn_acpi_slot_fixup(dev, pcidev_info); else sn_more_slot_fixup(dev, pcidev_info); @@ -498,7 +505,7 @@ void __devinit sn_pci_fixup_bus(struct pci_bus *bus) { - if (SN_ACPI_BASE_SUPPORT()) + if (sn_acpi_base_support()) sn_acpi_bus_fixup(bus); else sn_bus_fixup(bus); @@ -546,7 +553,7 @@ sn_io_early_init(void) printk(KERN_INFO "ACPI DSDT OEM Rev 0x%x\n", acpi_gbl_DSDT->oem_revision); - if (SN_ACPI_BASE_SUPPORT()) + if (sn_acpi_base_support()) sn_io_acpi_init(); else sn_io_init(); diff --git a/arch/ia64/sn/kernel/iomv.c b/arch/ia64/sn/kernel/iomv.c index 4aa4f30..b1a47da 100644 --- a/arch/ia64/sn/kernel/iomv.c +++ b/arch/ia64/sn/kernel/iomv.c @@ -1,4 +1,4 @@ -/* +/* * This file is subject to the terms and conditions of the GNU General Public * License. See the file "COPYING" in the main directory of this archive * for more details. @@ -16,7 +16,6 @@ #include #include #include -#include #define IS_LEGACY_VGA_IOPORT(p) \ (((p) >= 0x3b0 && (p) <= 0x3bb) || ((p) >= 0x3c0 && (p) <= 0x3df)) @@ -26,9 +25,12 @@ * @port: port to convert * * Legacy in/out instructions are converted to ld/st instructions - * on IA64. This routine will convert a port number into a valid + * on IA64. This routine will convert a port number into a valid * SN i/o address. Used by sn_in*() and sn_out*(). */ + +extern int sn_acpi_base_support(); + void *sn_io_addr(unsigned long port) { if (!IS_RUNNING_ON_SIMULATOR()) { @@ -37,7 +39,7 @@ void *sn_io_addr(unsigned long port) /* On sn2, legacy I/O ports don't point at anything */ if (port < (64 * 1024)) return NULL; - if (SN_ACPI_BASE_SUPPORT()) + if (sn_acpi_base_support()) return (__ia64_mk_io_addr(port)); else return ((void *)(port | __IA64_UNCACHED_OFFSET)); diff --git a/arch/x86_64/kernel/time.c b/arch/x86_64/kernel/time.c index 5cc76d0..335cc91 100644 --- a/arch/x86_64/kernel/time.c +++ b/arch/x86_64/kernel/time.c @@ -498,7 +498,7 @@ static unsigned long get_cmos_time(void) { unsigned int year, mon, day, hour, min, sec; unsigned long flags; - unsigned extyear = 0; + unsigned century = 0; spin_lock_irqsave(&rtc_lock, flags); @@ -510,9 +510,9 @@ static unsigned long get_cmos_time(void) mon = CMOS_READ(RTC_MONTH); year = CMOS_READ(RTC_YEAR); #ifdef CONFIG_ACPI - if (acpi_fadt.revision >= FADT2_REVISION_ID && - acpi_fadt.century) - extyear = CMOS_READ(acpi_fadt.century); + if (acpi_gbl_FADT.header.revision >= FADT2_REVISION_ID && + acpi_gbl_FADT.century) + century = CMOS_READ(acpi_gbl_FADT.century); #endif } while (sec != CMOS_READ(RTC_SECONDS)); @@ -530,10 +530,10 @@ static unsigned long get_cmos_time(void) BCD_TO_BIN(mon); BCD_TO_BIN(year); - if (extyear) { - BCD_TO_BIN(extyear); - year += extyear; - printk(KERN_INFO "Extended CMOS year: %d\n", extyear); + if (century) { + BCD_TO_BIN(century); + year += century * 100; + printk(KERN_INFO "Extended CMOS year: %d\n", century * 100); } else { /* * x86-64 systems only exists since 2002. @@ -954,7 +954,7 @@ __cpuinit int unsynchronized_tsc(void) if (boot_cpu_data.x86_vendor == X86_VENDOR_INTEL) { #ifdef CONFIG_ACPI /* But TSC doesn't tick in C3 so don't use it there */ - if (acpi_fadt.length > 0 && acpi_fadt.plvl3_lat < 1000) + if (acpi_gbl_FADT.header.length > 0 && acpi_gbl_FADT.C3latency < 1000) return 1; #endif return 0; diff --git a/drivers/acpi/asus_acpi.c b/drivers/acpi/asus_acpi.c index 396140b..31ad70a 100644 --- a/drivers/acpi/asus_acpi.c +++ b/drivers/acpi/asus_acpi.c @@ -26,7 +26,7 @@ * Pontus Fuchs - Helper functions, cleanup * Johann Wiesner - Small compile fixes * John Belmonte - ACPI code for Toshiba laptop was a good starting point. - * Éric Burghard - LED display support for W1N + * �ic Burghard - LED display support for W1N * */ @@ -1128,7 +1128,6 @@ static int asus_model_match(char *model) static int asus_hotk_get_info(void) { struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; - struct acpi_buffer dsdt = { ACPI_ALLOCATE_BUFFER, NULL }; union acpi_object *model = NULL; int bsts_result; char *string = NULL; @@ -1142,11 +1141,9 @@ static int asus_hotk_get_info(void) * HID), this bit will be moved. A global variable asus_info contains * the DSDT header. */ - status = acpi_get_table(ACPI_TABLE_ID_DSDT, 1, &dsdt); + status = acpi_get_table(ACPI_SIG_DSDT, 1, &asus_info); if (ACPI_FAILURE(status)) printk(KERN_WARNING " Couldn't get the DSDT table header\n"); - else - asus_info = dsdt.pointer; /* We have to write 0 on init this far for all ASUS models */ if (!write_acpi_int(hotk->handle, "INIT", 0, &buffer)) { @@ -1358,8 +1355,6 @@ static void __exit asus_acpi_exit(void) acpi_bus_unregister_driver(&asus_hotk_driver); remove_proc_entry(PROC_ASUS, acpi_root_dir); - kfree(asus_info); - return; } diff --git a/drivers/acpi/blacklist.c b/drivers/acpi/blacklist.c index f9c972b..bdc169b 100644 --- a/drivers/acpi/blacklist.c +++ b/drivers/acpi/blacklist.c @@ -44,7 +44,7 @@ struct acpi_blacklist_item { char oem_id[7]; char oem_table_id[9]; u32 oem_revision; - acpi_table_type table; + char *table; enum acpi_blacklist_predicates oem_revision_predicate; char *reason; u32 is_critical_error; @@ -56,18 +56,18 @@ struct acpi_blacklist_item { */ static struct acpi_blacklist_item acpi_blacklist[] __initdata = { /* Compaq Presario 1700 */ - {"PTLTD ", " DSDT ", 0x06040000, ACPI_DSDT, less_than_or_equal, + {"PTLTD ", " DSDT ", 0x06040000, ACPI_SIG_DSDT, less_than_or_equal, "Multiple problems", 1}, /* Sony FX120, FX140, FX150? */ - {"SONY ", "U0 ", 0x20010313, ACPI_DSDT, less_than_or_equal, + {"SONY ", "U0 ", 0x20010313, ACPI_SIG_DSDT, less_than_or_equal, "ACPI driver problem", 1}, /* Compaq Presario 800, Insyde BIOS */ - {"INT440", "SYSFexxx", 0x00001001, ACPI_DSDT, less_than_or_equal, + {"INT440", "SYSFexxx", 0x00001001, ACPI_SIG_DSDT, less_than_or_equal, "Does not use _REG to protect EC OpRegions", 1}, /* IBM 600E - _ADR should return 7, but it returns 1 */ - {"IBM ", "TP600E ", 0x00000105, ACPI_DSDT, less_than_or_equal, + {"IBM ", "TP600E ", 0x00000105, ACPI_SIG_DSDT, less_than_or_equal, "Incorrect _ADR", 1}, - {"ASUS\0\0", "P2B-S ", 0, ACPI_DSDT, all_versions, + {"ASUS\0\0", "P2B-S ", 0, ACPI_SIG_DSDT, all_versions, "Bogus PCI routing", 1}, {""} @@ -106,8 +106,7 @@ int __init acpi_blacklisted(void) struct acpi_table_header *table_header; while (acpi_blacklist[i].oem_id[0] != '\0') { - if (acpi_get_table_header_early - (acpi_blacklist[i].table, &table_header)) { + if (acpi_get_table_header(acpi_blacklist[i].table, 0, &table_header)) { i++; continue; } diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c index 766332e..cb807c4 100644 --- a/drivers/acpi/bus.c +++ b/drivers/acpi/bus.c @@ -44,9 +44,6 @@ ACPI_MODULE_NAME("acpi_bus") extern void __init acpi_pic_sci_set_trigger(unsigned int irq, u16 trigger); #endif -struct fadt_descriptor acpi_fadt; -EXPORT_SYMBOL(acpi_fadt); - struct acpi_device *acpi_root; struct proc_dir_entry *acpi_root_dir; EXPORT_SYMBOL(acpi_root_dir); @@ -582,11 +579,12 @@ static int __init acpi_bus_init_irq(void) return 0; } +acpi_native_uint acpi_gbl_permanent_mmap; + + void __init acpi_early_init(void) { acpi_status status = AE_OK; - struct acpi_buffer buffer = { sizeof(acpi_fadt), &acpi_fadt }; - if (acpi_disabled) return; @@ -597,6 +595,15 @@ void __init acpi_early_init(void) if (!acpi_strict) acpi_gbl_enable_interpreter_slack = TRUE; + acpi_gbl_permanent_mmap = 1; + + status = acpi_reallocate_root_table(); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR PREFIX + "Unable to reallocate ACPI tables\n"); + goto error0; + } + status = acpi_initialize_subsystem(); if (ACPI_FAILURE(status)) { printk(KERN_ERR PREFIX @@ -611,14 +618,6 @@ void __init acpi_early_init(void) goto error0; } - /* - * Get a separate copy of the FADT for use by other drivers. - */ - status = acpi_get_table(ACPI_TABLE_ID_FADT, 1, &buffer); - if (ACPI_FAILURE(status)) { - printk(KERN_ERR PREFIX "Unable to get the FADT\n"); - goto error0; - } #ifdef CONFIG_X86 if (!acpi_ioapic) { extern acpi_interrupt_flags acpi_sci_flags; diff --git a/drivers/acpi/ec.c b/drivers/acpi/ec.c index cbdf031..7a1f2ba 100644 --- a/drivers/acpi/ec.c +++ b/drivers/acpi/ec.c @@ -872,9 +872,7 @@ static int __init acpi_ec_get_real_ecdt(void) acpi_status status; struct acpi_table_ecdt *ecdt_ptr; - status = acpi_get_firmware_table("ECDT", 1, ACPI_LOGICAL_ADDRESSING, - (struct acpi_table_header **) - &ecdt_ptr); + status = acpi_get_table("ECDT", 1, (struct acpi_table_header **)&ecdt_ptr); if (ACPI_FAILURE(status)) return -ENODEV; diff --git a/drivers/acpi/motherboard.c b/drivers/acpi/motherboard.c index 2e17ec7..b61107b 100644 --- a/drivers/acpi/motherboard.c +++ b/drivers/acpi/motherboard.c @@ -134,41 +134,41 @@ static void __init acpi_request_region (struct acpi_generic_address *addr, if (!addr->address || !length) return; - if (addr->address_space_id == ACPI_ADR_SPACE_SYSTEM_IO) + if (addr->space_id == ACPI_ADR_SPACE_SYSTEM_IO) request_region(addr->address, length, desc); - else if (addr->address_space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) + else if (addr->space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) request_mem_region(addr->address, length, desc); } static void __init acpi_reserve_resources(void) { - acpi_request_region(&acpi_gbl_FADT->xpm1a_evt_blk, - acpi_gbl_FADT->pm1_evt_len, "ACPI PM1a_EVT_BLK"); + acpi_request_region(&acpi_gbl_FADT.xpm1a_event_block, + acpi_gbl_FADT.pm1_event_length, "ACPI PM1a_EVT_BLK"); - acpi_request_region(&acpi_gbl_FADT->xpm1b_evt_blk, - acpi_gbl_FADT->pm1_evt_len, "ACPI PM1b_EVT_BLK"); + acpi_request_region(&acpi_gbl_FADT.xpm1b_event_block, + acpi_gbl_FADT.pm1_event_length, "ACPI PM1b_EVT_BLK"); - acpi_request_region(&acpi_gbl_FADT->xpm1a_cnt_blk, - acpi_gbl_FADT->pm1_cnt_len, "ACPI PM1a_CNT_BLK"); + acpi_request_region(&acpi_gbl_FADT.xpm1a_control_block, + acpi_gbl_FADT.pm1_control_length, "ACPI PM1a_CNT_BLK"); - acpi_request_region(&acpi_gbl_FADT->xpm1b_cnt_blk, - acpi_gbl_FADT->pm1_cnt_len, "ACPI PM1b_CNT_BLK"); + acpi_request_region(&acpi_gbl_FADT.xpm1b_control_block, + acpi_gbl_FADT.pm1_control_length, "ACPI PM1b_CNT_BLK"); - if (acpi_gbl_FADT->pm_tm_len == 4) - acpi_request_region(&acpi_gbl_FADT->xpm_tmr_blk, 4, "ACPI PM_TMR"); + if (acpi_gbl_FADT.pm_timer_length == 4) + acpi_request_region(&acpi_gbl_FADT.xpm_timer_block, 4, "ACPI PM_TMR"); - acpi_request_region(&acpi_gbl_FADT->xpm2_cnt_blk, - acpi_gbl_FADT->pm2_cnt_len, "ACPI PM2_CNT_BLK"); + acpi_request_region(&acpi_gbl_FADT.xpm2_control_block, + acpi_gbl_FADT.pm2_control_length, "ACPI PM2_CNT_BLK"); /* Length of GPE blocks must be a non-negative multiple of 2 */ - if (!(acpi_gbl_FADT->gpe0_blk_len & 0x1)) - acpi_request_region(&acpi_gbl_FADT->xgpe0_blk, - acpi_gbl_FADT->gpe0_blk_len, "ACPI GPE0_BLK"); + if (!(acpi_gbl_FADT.gpe0_block_length & 0x1)) + acpi_request_region(&acpi_gbl_FADT.xgpe0_block, + acpi_gbl_FADT.gpe0_block_length, "ACPI GPE0_BLK"); - if (!(acpi_gbl_FADT->gpe1_blk_len & 0x1)) - acpi_request_region(&acpi_gbl_FADT->xgpe1_blk, - acpi_gbl_FADT->gpe1_blk_len, "ACPI GPE1_BLK"); + if (!(acpi_gbl_FADT.gpe1_block_length & 0x1)) + acpi_request_region(&acpi_gbl_FADT.xgpe1_block, + acpi_gbl_FADT.gpe1_block_length, "ACPI GPE1_BLK"); } static int __init acpi_motherboard_init(void) diff --git a/drivers/acpi/osl.c b/drivers/acpi/osl.c index 57ae1e5..c1c2100 100644 --- a/drivers/acpi/osl.c +++ b/drivers/acpi/osl.c @@ -36,6 +36,7 @@ #include #include #include +#include #include #include #include @@ -136,53 +137,43 @@ void acpi_os_vprintf(const char *fmt, va_list args) #endif } -acpi_status acpi_os_get_root_pointer(u32 flags, struct acpi_pointer *addr) +acpi_physical_address __init acpi_os_get_root_pointer(void) { if (efi_enabled) { - addr->pointer_type = ACPI_PHYSICAL_POINTER; if (efi.acpi20 != EFI_INVALID_TABLE_ADDR) - addr->pointer.physical = efi.acpi20; + return efi.acpi20; else if (efi.acpi != EFI_INVALID_TABLE_ADDR) - addr->pointer.physical = efi.acpi; + return efi.acpi; else { printk(KERN_ERR PREFIX "System description tables not found\n"); - return AE_NOT_FOUND; + return 0; } - } else { - if (ACPI_FAILURE(acpi_find_root_pointer(flags, addr))) { - printk(KERN_ERR PREFIX - "System description tables not found\n"); - return AE_NOT_FOUND; - } - } - - return AE_OK; + } else + return acpi_find_rsdp(); } -acpi_status -acpi_os_map_memory(acpi_physical_address phys, acpi_size size, - void __iomem ** virt) +void __iomem *acpi_os_map_memory(acpi_physical_address phys, acpi_size size) { if (phys > ULONG_MAX) { printk(KERN_ERR PREFIX "Cannot map memory that high\n"); - return AE_BAD_PARAMETER; + return 0; } - /* - * ioremap checks to ensure this is in reserved space - */ - *virt = ioremap((unsigned long)phys, size); - - if (!*virt) - return AE_NO_MEMORY; - - return AE_OK; + if (acpi_gbl_permanent_mmap) + /* + * ioremap checks to ensure this is in reserved space + */ + return ioremap((unsigned long)phys, size); + else + return __acpi_map_table((unsigned long)phys, size); } EXPORT_SYMBOL_GPL(acpi_os_map_memory); void acpi_os_unmap_memory(void __iomem * virt, acpi_size size) { - iounmap(virt); + if (acpi_gbl_permanent_mmap) { + iounmap(virt); + } } EXPORT_SYMBOL_GPL(acpi_os_unmap_memory); diff --git a/drivers/acpi/processor_core.c b/drivers/acpi/processor_core.c index 5f9496d..4d552f7 100644 --- a/drivers/acpi/processor_core.c +++ b/drivers/acpi/processor_core.c @@ -431,7 +431,7 @@ static int acpi_processor_get_info(struct acpi_processor *pr) * Check to see if we have bus mastering arbitration control. This * is required for proper C3 usage (to maintain cache coherency). */ - if (acpi_fadt.V1_pm2_cnt_blk && acpi_fadt.pm2_cnt_len) { + if (acpi_fadt.pm2_control_block && acpi_fadt.pm2_control_length) { pr->flags.bm_control = 1; ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Bus mastering arbitration control present\n")); diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c index 3f30af2..9fa3d39 100644 --- a/drivers/acpi/processor_idle.c +++ b/drivers/acpi/processor_idle.c @@ -160,7 +160,7 @@ static inline u32 ticks_elapsed(u32 t1, u32 t2) { if (t2 >= t1) return (t2 - t1); - else if (!acpi_fadt.tmr_val_ext) + else if (!(acpi_fadt.flags & ACPI_FADT_32BIT_TIMER)) return (((0x00FFFFFF - t1) + t2) & 0x00FFFFFF); else return ((0xFFFFFFFF - t1) + t2); @@ -236,7 +236,7 @@ static void acpi_cstate_enter(struct acpi_processor_cx *cstate) /* Dummy wait op - must do something useless after P_LVL2 read because chipsets cannot guarantee that STPCLK# signal gets asserted in time to freeze execution properly. */ - unused = inl(acpi_fadt.xpm_tmr_blk.address); + unused = inl(acpi_fadt.xpm_timer_block.address); } } @@ -338,7 +338,7 @@ static void acpi_processor_idle(void) * detection phase, to work cleanly with logical CPU hotplug. */ if ((cx->type != ACPI_STATE_C1) && (num_online_cpus() > 1) && - !pr->flags.has_cst && !acpi_fadt.plvl2_up) + !pr->flags.has_cst && !(acpi_fadt.flags & ACPI_FADT_C2_MP_SUPPORTED)) cx = &pr->power.states[ACPI_STATE_C1]; #endif @@ -384,11 +384,11 @@ static void acpi_processor_idle(void) case ACPI_STATE_C2: /* Get start time (ticks) */ - t1 = inl(acpi_fadt.xpm_tmr_blk.address); + t1 = inl(acpi_fadt.xpm_timer_block.address); /* Invoke C2 */ acpi_cstate_enter(cx); /* Get end time (ticks) */ - t2 = inl(acpi_fadt.xpm_tmr_blk.address); + t2 = inl(acpi_fadt.xpm_timer_block.address); #ifdef CONFIG_GENERIC_TIME /* TSC halts in C2, so notify users */ @@ -420,11 +420,11 @@ static void acpi_processor_idle(void) } /* Get start time (ticks) */ - t1 = inl(acpi_fadt.xpm_tmr_blk.address); + t1 = inl(acpi_fadt.xpm_timer_block.address); /* Invoke C3 */ acpi_cstate_enter(cx); /* Get end time (ticks) */ - t2 = inl(acpi_fadt.xpm_tmr_blk.address); + t2 = inl(acpi_fadt.xpm_timer_block.address); if (pr->flags.bm_check) { /* Enable bus master arbitration */ atomic_dec(&c3_cpu_count); @@ -457,7 +457,7 @@ static void acpi_processor_idle(void) #ifdef CONFIG_HOTPLUG_CPU /* Don't do promotion/demotion */ if ((cx->type == ACPI_STATE_C1) && (num_online_cpus() > 1) && - !pr->flags.has_cst && !acpi_fadt.plvl2_up) { + !pr->flags.has_cst && !(acpi_fadt.flags & ACPI_FADT_C2_MP_SUPPORTED)) { next_state = cx; goto end; } @@ -627,7 +627,8 @@ static int acpi_processor_get_power_info_fadt(struct acpi_processor *pr) * Check for P_LVL2_UP flag before entering C2 and above on * an SMP system. */ - if ((num_online_cpus() > 1) && !acpi_fadt.plvl2_up) + if ((num_online_cpus() > 1) && + !(acpi_fadt.flags & ACPI_FADT_C2_MP_SUPPORTED)) return -ENODEV; #endif @@ -636,8 +637,8 @@ static int acpi_processor_get_power_info_fadt(struct acpi_processor *pr) pr->power.states[ACPI_STATE_C3].address = pr->pblk + 5; /* determine latencies from FADT */ - pr->power.states[ACPI_STATE_C2].latency = acpi_fadt.plvl2_lat; - pr->power.states[ACPI_STATE_C3].latency = acpi_fadt.plvl3_lat; + pr->power.states[ACPI_STATE_C2].latency = acpi_fadt.C2latency; + pr->power.states[ACPI_STATE_C3].latency = acpi_fadt.C3latency; ACPI_DEBUG_PRINT((ACPI_DB_INFO, "lvl2[0x%08x] lvl3[0x%08x]\n", @@ -883,7 +884,7 @@ static void acpi_processor_power_verify_c3(struct acpi_processor *pr, * WBINVD should be set in fadt, for C3 state to be * supported on when bm_check is not required. */ - if (acpi_fadt.wb_invd != 1) { + if (!(acpi_fadt.flags & ACPI_FADT_WBINVD)) { ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Cache invalidation should work properly" " for C3 to be enabled on SMP systems\n")); @@ -1164,9 +1165,9 @@ int __cpuinit acpi_processor_power_init(struct acpi_processor *pr, if (!pr) return -EINVAL; - if (acpi_fadt.cst_cnt && !nocst) { + if (acpi_fadt.cst_control && !nocst) { status = - acpi_os_write_port(acpi_fadt.smi_cmd, acpi_fadt.cst_cnt, 8); + acpi_os_write_port(acpi_fadt.smi_command, acpi_fadt.cst_control, 8); if (ACPI_FAILURE(status)) { ACPI_EXCEPTION((AE_INFO, status, "Notifying BIOS of _CST ability failed")); diff --git a/drivers/acpi/processor_perflib.c b/drivers/acpi/processor_perflib.c index cbb6f08..aabb988 100644 --- a/drivers/acpi/processor_perflib.c +++ b/drivers/acpi/processor_perflib.c @@ -352,31 +352,24 @@ int acpi_processor_notify_smm(struct module *calling_module) is_done = -EIO; - /* Can't write pstate_cnt to smi_cmd if either value is zero */ - if ((!acpi_fadt.smi_cmd) || (!acpi_fadt.pstate_cnt)) { - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "No SMI port or pstate_cnt\n")); + /* Can't write pstate_control to smi_command if either value is zero */ + if ((!acpi_fadt.smi_command) || (!acpi_fadt.pstate_control)) { + ACPI_DEBUG_PRINT((ACPI_DB_INFO, "No SMI port or pstate_control\n")); module_put(calling_module); return 0; } ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Writing pstate_cnt [0x%x] to smi_cmd [0x%x]\n", - acpi_fadt.pstate_cnt, acpi_fadt.smi_cmd)); + "Writing pstate_control [0x%x] to smi_command [0x%x]\n", + acpi_fadt.pstate_control, acpi_fadt.smi_command)); - /* FADT v1 doesn't support pstate_cnt, many BIOS vendors use - * it anyway, so we need to support it... */ - if (acpi_fadt_is_v1) { - ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "Using v1.0 FADT reserved value for pstate_cnt\n")); - } - - status = acpi_os_write_port(acpi_fadt.smi_cmd, - (u32) acpi_fadt.pstate_cnt, 8); + status = acpi_os_write_port(acpi_fadt.smi_command, + (u32) acpi_fadt.pstate_control, 8); if (ACPI_FAILURE(status)) { ACPI_EXCEPTION((AE_INFO, status, - "Failed to write pstate_cnt [0x%x] to " - "smi_cmd [0x%x]", acpi_fadt.pstate_cnt, - acpi_fadt.smi_cmd)); + "Failed to write pstate_control [0x%x] to " + "smi_command [0x%x]", acpi_fadt.pstate_control, + acpi_fadt.smi_command)); module_put(calling_module); return status; } diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 283d875..b1692b1 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -1333,7 +1333,7 @@ static int acpi_bus_scan_fixed(struct acpi_device *root) /* * Enumerate all fixed-feature devices. */ - if (acpi_fadt.pwr_button == 0) { + if ((acpi_fadt.flags & ACPI_FADT_POWER_BUTTON) == 0) { result = acpi_add_single_object(&device, acpi_root, NULL, ACPI_BUS_TYPE_POWER_BUTTON); @@ -1341,7 +1341,7 @@ static int acpi_bus_scan_fixed(struct acpi_device *root) result = acpi_start_single_object(device); } - if (acpi_fadt.sleep_button == 0) { + if ((acpi_fadt.flags & ACPI_FADT_SLEEP_BUTTON) == 0) { result = acpi_add_single_object(&device, acpi_root, NULL, ACPI_BUS_TYPE_SLEEP_BUTTON); diff --git a/drivers/acpi/sleep/proc.c b/drivers/acpi/sleep/proc.c index 3496257..ccc11b3 100644 --- a/drivers/acpi/sleep/proc.c +++ b/drivers/acpi/sleep/proc.c @@ -73,7 +73,7 @@ acpi_system_write_sleep(struct file *file, static int acpi_system_alarm_seq_show(struct seq_file *seq, void *offset) { u32 sec, min, hr; - u32 day, mo, yr; + u32 day, mo, yr, cent = 0; unsigned char rtc_control = 0; unsigned long flags; @@ -87,20 +87,19 @@ static int acpi_system_alarm_seq_show(struct seq_file *seq, void *offset) rtc_control = CMOS_READ(RTC_CONTROL); /* If we ever get an FACP with proper values... */ - if (acpi_gbl_FADT->day_alrm) + if (acpi_gbl_FADT.day_alarm) /* ACPI spec: only low 6 its should be cared */ - day = CMOS_READ(acpi_gbl_FADT->day_alrm) & 0x3F; + day = CMOS_READ(acpi_gbl_FADT.day_alarm) & 0x3F; else day = CMOS_READ(RTC_DAY_OF_MONTH); - if (acpi_gbl_FADT->mon_alrm) - mo = CMOS_READ(acpi_gbl_FADT->mon_alrm); + if (acpi_gbl_FADT.month_alarm) + mo = CMOS_READ(acpi_gbl_FADT.month_alarm); else mo = CMOS_READ(RTC_MONTH); - if (acpi_gbl_FADT->century) - yr = CMOS_READ(acpi_gbl_FADT->century) * 100 + - CMOS_READ(RTC_YEAR); - else - yr = CMOS_READ(RTC_YEAR); + if (acpi_gbl_FADT.century) + cent = CMOS_READ(acpi_gbl_FADT.century); + + yr = CMOS_READ(RTC_YEAR); spin_unlock_irqrestore(&rtc_lock, flags); @@ -111,10 +110,11 @@ static int acpi_system_alarm_seq_show(struct seq_file *seq, void *offset) BCD_TO_BIN(day); BCD_TO_BIN(mo); BCD_TO_BIN(yr); + BCD_TO_BIN(cent); } /* we're trusting the FADT (see above) */ - if (!acpi_gbl_FADT->century) + if (!acpi_gbl_FADT.century) /* If we're not trusting the FADT, we should at least make it * right for _this_ century... ehm, what is _this_ century? * @@ -134,6 +134,8 @@ static int acpi_system_alarm_seq_show(struct seq_file *seq, void *offset) * */ yr += 2000; + else + yr += cent * 100; seq_printf(seq, "%4.4u-", yr); (mo > 12) ? seq_puts(seq, "**-") : seq_printf(seq, "%2.2u-", mo); @@ -317,12 +319,12 @@ acpi_system_write_alarm(struct file *file, * offsets into the CMOS RAM here -- which for some reason are pointing * to the RTC area of memory. */ - if (acpi_gbl_FADT->day_alrm) - CMOS_WRITE(day, acpi_gbl_FADT->day_alrm); - if (acpi_gbl_FADT->mon_alrm) - CMOS_WRITE(mo, acpi_gbl_FADT->mon_alrm); - if (acpi_gbl_FADT->century) - CMOS_WRITE(yr / 100, acpi_gbl_FADT->century); + if (acpi_gbl_FADT.day_alarm) + CMOS_WRITE(day, acpi_gbl_FADT.day_alarm); + if (acpi_gbl_FADT.month_alarm) + CMOS_WRITE(mo, acpi_gbl_FADT.month_alarm); + if (acpi_gbl_FADT.century) + CMOS_WRITE(yr / 100, acpi_gbl_FADT.century); /* enable the rtc alarm interrupt */ rtc_control |= RTC_AIE; CMOS_WRITE(rtc_control, RTC_CONTROL); diff --git a/drivers/acpi/system.c b/drivers/acpi/system.c index d86dcb3..2d425d8 100644 --- a/drivers/acpi/system.c +++ b/drivers/acpi/system.c @@ -39,7 +39,6 @@ ACPI_MODULE_NAME("acpi_system") #define ACPI_SYSTEM_FILE_EVENT "event" #define ACPI_SYSTEM_FILE_DSDT "dsdt" #define ACPI_SYSTEM_FILE_FADT "fadt" -extern struct fadt_descriptor acpi_fadt; /* -------------------------------------------------------------------------- FS Interface (/proc) @@ -76,17 +75,16 @@ acpi_system_read_dsdt(struct file *file, char __user * buffer, size_t count, loff_t * ppos) { acpi_status status = AE_OK; - struct acpi_buffer dsdt = { ACPI_ALLOCATE_BUFFER, NULL }; + struct acpi_table_header *dsdt = NULL; ssize_t res; - status = acpi_get_table(ACPI_TABLE_ID_DSDT, 1, &dsdt); + status = acpi_get_table(ACPI_SIG_DSDT, 1, &dsdt); if (ACPI_FAILURE(status)) return -ENODEV; res = simple_read_from_buffer(buffer, count, ppos, - dsdt.pointer, dsdt.length); - kfree(dsdt.pointer); + dsdt, dsdt->length); return res; } @@ -103,17 +101,16 @@ acpi_system_read_fadt(struct file *file, char __user * buffer, size_t count, loff_t * ppos) { acpi_status status = AE_OK; - struct acpi_buffer fadt = { ACPI_ALLOCATE_BUFFER, NULL }; + struct acpi_table_header *fadt = NULL; ssize_t res; - status = acpi_get_table(ACPI_TABLE_ID_FADT, 1, &fadt); + status = acpi_get_table(ACPI_SIG_FADT, 1, &fadt); if (ACPI_FAILURE(status)) return -ENODEV; res = simple_read_from_buffer(buffer, count, ppos, - fadt.pointer, fadt.length); - kfree(fadt.pointer); + fadt, fadt->length); return res; } diff --git a/drivers/acpi/tables.c b/drivers/acpi/tables.c index ffa30c9..5bb1431 100644 --- a/drivers/acpi/tables.c +++ b/drivers/acpi/tables.c @@ -74,6 +74,7 @@ static unsigned long sdt_pa; /* Physical Address */ static unsigned long sdt_count; /* Table count */ static struct acpi_table_sdt sdt_entry[ACPI_MAX_TABLES] __initdata; +static struct acpi_table_desc initial_tables[ACPI_MAX_TABLES] __initdata; void acpi_table_print(struct acpi_table_header *header, unsigned long phys_addr) { @@ -284,12 +285,12 @@ acpi_get_table_header_early(enum acpi_table_id id, struct fadt_descriptor *fadt = (struct fadt_descriptor *)*header; - if (fadt->revision == 3 && fadt->Xdsdt) { + if (fadt->header.revision == 3 && fadt->Xdsdt) { *header = (void *)__acpi_map_table(fadt->Xdsdt, sizeof(struct acpi_table_header)); - } else if (fadt->V1_dsdt) { - *header = (void *)__acpi_map_table(fadt->V1_dsdt, + } else if (fadt->dsdt) { + *header = (void *)__acpi_map_table(fadt->dsdt, sizeof(struct acpi_table_header)); } else @@ -410,12 +411,11 @@ static int __init acpi_table_get_sdt(struct acpi_table_rsdp *rsdp) /* First check XSDT (but only on ACPI 2.0-compatible systems) */ - if ((rsdp->revision >= 2) && - (((struct acpi20_table_rsdp *)rsdp)->xsdt_address)) { + if ((rsdp->revision >= 2) && rsdp->xsdt_physical_address) { struct acpi_table_xsdt *mapped_xsdt = NULL; - sdt_pa = ((struct acpi20_table_rsdp *)rsdp)->xsdt_address; + sdt_pa = rsdp->xsdt_physical_address; /* map in just the header */ header = (struct acpi_table_header *) @@ -457,16 +457,16 @@ static int __init acpi_table_get_sdt(struct acpi_table_rsdp *rsdp) } for (i = 0; i < sdt_count; i++) - sdt_entry[i].pa = (unsigned long)mapped_xsdt->entry[i]; + sdt_entry[i].pa = (unsigned long)mapped_xsdt->table_offset_entry[i]; } /* Then check RSDT */ - else if (rsdp->rsdt_address) { + else if (rsdp->rsdt_physical_address) { struct acpi_table_rsdt *mapped_rsdt = NULL; - sdt_pa = rsdp->rsdt_address; + sdt_pa = rsdp->rsdt_physical_address; /* map in just the header */ header = (struct acpi_table_header *) @@ -507,7 +507,7 @@ static int __init acpi_table_get_sdt(struct acpi_table_rsdp *rsdp) } for (i = 0; i < sdt_count; i++) - sdt_entry[i].pa = (unsigned long)mapped_rsdt->entry[i]; + sdt_entry[i].pa = (unsigned long)mapped_rsdt->table_offset_entry[i]; } else { @@ -599,13 +599,10 @@ int __init acpi_table_init(void) if (rsdp->revision < 2) result = - acpi_table_compute_checksum(rsdp, - sizeof(struct acpi_table_rsdp)); + acpi_table_compute_checksum(rsdp, ACPI_RSDP_REV0_SIZE); else result = - acpi_table_compute_checksum(rsdp, - ((struct acpi20_table_rsdp *) - rsdp)->length); + acpi_table_compute_checksum(rsdp, rsdp->length); if (result) { printk(KERN_WARNING " >>> ERROR: Invalid checksum\n"); @@ -617,5 +614,7 @@ int __init acpi_table_init(void) if (acpi_table_get_sdt(rsdp)) return -ENODEV; + acpi_initialize_tables(initial_tables, ACPI_MAX_TABLES, 0); + return 0; } diff --git a/drivers/acpi/tables/Makefile b/drivers/acpi/tables/Makefile index aa4c695..f08f1f3 100644 --- a/drivers/acpi/tables/Makefile +++ b/drivers/acpi/tables/Makefile @@ -2,7 +2,6 @@ # Makefile for all Linux ACPI interpreter subdirectories # -obj-y := tbconvrt.o tbget.o tbrsdt.o tbxface.o \ - tbgetall.o tbinstal.o tbutils.o tbxfroot.o +obj-y := tbxface.o tbinstal.o tbutils.o tbfind.o EXTRA_CFLAGS += $(ACPI_CFLAGS) diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 8e44f83..6d13737 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -545,7 +545,7 @@ acpi_tb_get_root_table_entry(u8 * table_entry, * ******************************************************************************/ -acpi_status +acpi_status __init acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags) { struct acpi_table_rsdp *rsdp; diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 13e8d66..94544a6 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -78,7 +78,7 @@ static acpi_status acpi_tb_load_namespace(void); * ******************************************************************************/ -acpi_status +acpi_status __init acpi_initialize_tables(struct acpi_table_desc *initial_table_array, u32 initial_table_count, u8 allow_resize) { @@ -132,8 +132,6 @@ acpi_initialize_tables(struct acpi_table_desc *initial_table_array, return_ACPI_STATUS(status); } -ACPI_EXPORT_SYMBOL(acpi_initialize_tables) - /******************************************************************************* * * FUNCTION: acpi_reallocate_root_table @@ -365,6 +363,10 @@ acpi_get_table(char *signature, *out_table = acpi_gbl_root_table_list.tables[i].pointer; } + if (!acpi_gbl_permanent_mmap) { + acpi_gbl_root_table_list.tables[i].pointer = 0; + } + return (status); } diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index 82d42b8..bd0fe7c 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -147,6 +147,8 @@ ACPI_EXTERN u8 ACPI_INIT_GLOBAL(acpi_gbl_leave_wake_gpes_disabled, TRUE); */ ACPI_EXTERN struct acpi_internal_rsdt acpi_gbl_root_table_list; ACPI_EXTERN struct acpi_table_fadt acpi_gbl_FADT; +#define acpi_fadt acpi_gbl_FADT +extern acpi_native_uint acpi_gbl_permanent_mmap; /* * Handle both ACPI 1.0 and ACPI 2.0 Integer widths. The integer width is diff --git a/include/acpi/acpi_bus.h b/include/acpi/acpi_bus.h index fdd1095..aef0e55 100644 --- a/include/acpi/acpi_bus.h +++ b/include/acpi/acpi_bus.h @@ -59,7 +59,6 @@ acpi_evaluate_reference(acpi_handle handle, #define ACPI_BUS_FILE_ROOT "acpi" extern struct proc_dir_entry *acpi_root_dir; -extern struct fadt_descriptor acpi_fadt; enum acpi_bus_removal_type { ACPI_BUS_REMOVAL_NORMAL = 0, diff --git a/include/acpi/actbl.h b/include/acpi/actbl.h index aed49a5..6f63b3b 100644 --- a/include/acpi/actbl.h +++ b/include/acpi/actbl.h @@ -236,6 +236,9 @@ struct acpi_table_fadt { struct acpi_generic_address xgpe1_block; /* 64-bit Extended General Purpose Event 1 Reg Blk address */ }; +#define fadt_descriptor acpi_table_fadt +#define sci_int sci_interrupt + /* FADT flags */ #define ACPI_FADT_WBINVD (1) /* 00: The wbinvd instruction works properly */ @@ -289,6 +292,8 @@ enum acpi_prefered_pm_profiles { /* * Get the remaining ACPI tables */ +/* + Don't include any new tables definitions for now. #include - +*/ #endif /* __ACTBL_H__ */ diff --git a/include/acpi/actbl2.h b/include/acpi/actbl2.h deleted file mode 100644 index 67efe6c..0000000 --- a/include/acpi/actbl2.h +++ /dev/null @@ -1,49 +0,0 @@ -/****************************************************************************** - * - * Name: actbl2.h - ACPI Specification Revision 2.0 Tables - * - *****************************************************************************/ - -/* - * Copyright (C) 2000 - 2006, R. Byron Moore - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions, and the following disclaimer, - * without modification. - * 2. Redistributions in binary form must reproduce at minimum a disclaimer - * substantially similar to the "NO WARRANTY" disclaimer below - * ("Disclaimer") and any redistribution must be conditioned upon - * including a substantially similar Disclaimer requirement for further - * binary redistribution. - * 3. Neither the names of the above-listed copyright holders nor the names - * of any contributors may be used to endorse or promote products derived - * from this software without specific prior written permission. - * - * Alternatively, this software may be distributed under the terms of the - * GNU General Public License ("GPL") version 2 as published by the Free - * Software Foundation. - * - * NO WARRANTY - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING - * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGES. - */ - -#ifndef __ACTBL2_H__ -#define __ACTBL2_H__ - -/* Code moved to both actbl.h and actbl1.h */ - -#endif /* __ACTBL2_H__ */ diff --git a/include/acpi/actbl71.h b/include/acpi/actbl71.h deleted file mode 100644 index 10ac05b..0000000 --- a/include/acpi/actbl71.h +++ /dev/null @@ -1,134 +0,0 @@ -/****************************************************************************** - * - * Name: actbl71.h - IA-64 Extensions to the ACPI Spec Rev. 0.71 - * This file includes tables specific to this - * specification revision. - * - *****************************************************************************/ - -/* - * Copyright (C) 2000 - 2003, R. Byron Moore - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -#ifndef __ACTBL71_H__ -#define __ACTBL71_H__ - -/* 0.71 FADT address_space data item bitmasks defines */ -/* If the associated bit is zero then it is in memory space else in io space */ - -#define SMI_CMD_ADDRESS_SPACE 0x01 -#define PM1_BLK_ADDRESS_SPACE 0x02 -#define PM2_CNT_BLK_ADDRESS_SPACE 0x04 -#define PM_TMR_BLK_ADDRESS_SPACE 0x08 -#define GPE0_BLK_ADDRESS_SPACE 0x10 -#define GPE1_BLK_ADDRESS_SPACE 0x20 - -/* Only for clarity in declarations */ - -typedef u64 IO_ADDRESS; - -#pragma pack(1) -struct { /* Root System Descriptor Pointer */ - NATIVE_CHAR signature[8]; /* contains "RSD PTR " */ - u8 checksum; /* to make sum of struct == 0 */ - NATIVE_CHAR oem_id[6]; /* OEM identification */ - u8 reserved; /* Must be 0 for 1.0, 2 for 2.0 */ - u64 rsdt_physical_address; /* 64-bit physical address of RSDT */ -}; - -/*****************************************/ -/* IA64 Extensions to ACPI Spec Rev 0.71 */ -/* for the Root System Description Table */ -/*****************************************/ -struct { - struct acpi_table_header header; /* Table header */ - u32 reserved_pad; /* IA64 alignment, must be 0 */ - u64 table_offset_entry[1]; /* Array of pointers to other */ - /* tables' headers */ -}; - -/*******************************************/ -/* IA64 Extensions to ACPI Spec Rev 0.71 */ -/* for the Firmware ACPI Control Structure */ -/*******************************************/ -struct { - NATIVE_CHAR signature[4]; /* signature "FACS" */ - u32 length; /* length of structure, in bytes */ - u32 hardware_signature; /* hardware configuration signature */ - u32 reserved4; /* must be 0 */ - u64 firmware_waking_vector; /* ACPI OS waking vector */ - u64 global_lock; /* Global Lock */ - u32 S4bios_f:1; /* Indicates if S4BIOS support is present */ - u32 reserved1:31; /* must be 0 */ - u8 reserved3[28]; /* reserved - must be zero */ -}; - -/******************************************/ -/* IA64 Extensions to ACPI Spec Rev 0.71 */ -/* for the Fixed ACPI Description Table */ -/******************************************/ -struct { - struct acpi_table_header header; /* table header */ - u32 reserved_pad; /* IA64 alignment, must be 0 */ - u64 firmware_ctrl; /* 64-bit Physical address of FACS */ - u64 dsdt; /* 64-bit Physical address of DSDT */ - u8 model; /* System Interrupt Model */ - u8 address_space; /* Address Space Bitmask */ - u16 sci_int; /* System vector of SCI interrupt */ - u8 acpi_enable; /* value to write to smi_cmd to enable ACPI */ - u8 acpi_disable; /* value to write to smi_cmd to disable ACPI */ - u8 S4bios_req; /* Value to write to SMI CMD to enter S4BIOS state */ - u8 reserved2; /* reserved - must be zero */ - u64 smi_cmd; /* Port address of SMI command port */ - u64 pm1a_evt_blk; /* Port address of Power Mgt 1a acpi_event Reg Blk */ - u64 pm1b_evt_blk; /* Port address of Power Mgt 1b acpi_event Reg Blk */ - u64 pm1a_cnt_blk; /* Port address of Power Mgt 1a Control Reg Blk */ - u64 pm1b_cnt_blk; /* Port address of Power Mgt 1b Control Reg Blk */ - u64 pm2_cnt_blk; /* Port address of Power Mgt 2 Control Reg Blk */ - u64 pm_tmr_blk; /* Port address of Power Mgt Timer Ctrl Reg Blk */ - u64 gpe0_blk; /* Port addr of General Purpose acpi_event 0 Reg Blk */ - u64 gpe1_blk; /* Port addr of General Purpose acpi_event 1 Reg Blk */ - u8 pm1_evt_len; /* Byte length of ports at pm1_x_evt_blk */ - u8 pm1_cnt_len; /* Byte length of ports at pm1_x_cnt_blk */ - u8 pm2_cnt_len; /* Byte Length of ports at pm2_cnt_blk */ - u8 pm_tm_len; /* Byte Length of ports at pm_tm_blk */ - u8 gpe0_blk_len; /* Byte Length of ports at gpe0_blk */ - u8 gpe1_blk_len; /* Byte Length of ports at gpe1_blk */ - u8 gpe1_base; /* offset in gpe model where gpe1 events start */ - u8 reserved3; /* reserved */ - u16 plvl2_lat; /* worst case HW latency to enter/exit C2 state */ - u16 plvl3_lat; /* worst case HW latency to enter/exit C3 state */ - u8 day_alrm; /* index to day-of-month alarm in RTC CMOS RAM */ - u8 mon_alrm; /* index to month-of-year alarm in RTC CMOS RAM */ - u8 century; /* index to century in RTC CMOS RAM */ - u8 reserved4; /* reserved */ - u32 flush_cash:1; /* PAL_FLUSH_CACHE is correctly supported */ - u32 reserved5:1; /* reserved - must be zero */ - u32 proc_c1:1; /* all processors support C1 state */ - u32 plvl2_up:1; /* C2 state works on MP system */ - u32 pwr_button:1; /* Power button is handled as a generic feature */ - u32 sleep_button:1; /* Sleep button is handled as a generic feature, or not present */ - u32 fixed_rTC:1; /* RTC wakeup stat not in fixed register space */ - u32 rtcs4:1; /* RTC wakeup stat not possible from S4 */ - u32 tmr_val_ext:1; /* tmr_val is 32 bits */ - u32 dock_cap:1; /* Supports Docking */ - u32 reserved6:22; /* reserved - must be zero */ -}; - -#pragma pack() - -#endif /* __ACTBL71_H__ */ diff --git a/include/asm-i386/acpi.h b/include/asm-i386/acpi.h index 7cfad93..0fb0c01 100644 --- a/include/asm-i386/acpi.h +++ b/include/asm-i386/acpi.h @@ -59,11 +59,11 @@ int __acpi_acquire_global_lock(unsigned int *lock); int __acpi_release_global_lock(unsigned int *lock); -#define ACPI_ACQUIRE_GLOBAL_LOCK(GLptr, Acq) \ - ((Acq) = __acpi_acquire_global_lock((unsigned int *) GLptr)) +#define ACPI_ACQUIRE_GLOBAL_LOCK(facs, Acq) \ + ((Acq) = __acpi_acquire_global_lock(&facs->global_lock)) -#define ACPI_RELEASE_GLOBAL_LOCK(GLptr, Acq) \ - ((Acq) = __acpi_release_global_lock((unsigned int *) GLptr)) +#define ACPI_RELEASE_GLOBAL_LOCK(facs, Acq) \ + ((Acq) = __acpi_release_global_lock(&facs->global_lock)) /* * Math helper asm macros diff --git a/include/asm-ia64/acpi.h b/include/asm-ia64/acpi.h index 09a5dd0..dba34d5 100644 --- a/include/asm-ia64/acpi.h +++ b/include/asm-ia64/acpi.h @@ -82,11 +82,11 @@ ia64_acpi_release_global_lock (unsigned int *lock) return old & 0x1; } -#define ACPI_ACQUIRE_GLOBAL_LOCK(GLptr, Acq) \ - ((Acq) = ia64_acpi_acquire_global_lock((unsigned int *) GLptr)) +#define ACPI_ACQUIRE_GLOBAL_LOCK(facs, Acq) \ + ((Acq) = ia64_acpi_acquire_global_lock(&facs->global_lock)) -#define ACPI_RELEASE_GLOBAL_LOCK(GLptr, Acq) \ - ((Acq) = ia64_acpi_release_global_lock((unsigned int *) GLptr)) +#define ACPI_RELEASE_GLOBAL_LOCK(facs, Acq) \ + ((Acq) = ia64_acpi_release_global_lock(&facs->global_lock)) #define acpi_disabled 0 /* ACPI always enabled on IA64 */ #define acpi_noirq 0 /* ACPI always enabled on IA64 */ diff --git a/include/asm-ia64/sn/acpi.h b/include/asm-ia64/sn/acpi.h deleted file mode 100644 index 2850a7e..0000000 --- a/include/asm-ia64/sn/acpi.h +++ /dev/null @@ -1,16 +0,0 @@ -/* - * This file is subject to the terms and conditions of the GNU General Public - * License. See the file "COPYING" in the main directory of this archive - * for more details. - * - * Copyright (C) 2006 Silicon Graphics, Inc. All rights reserved. - */ - -#ifndef _ASM_IA64_SN_ACPI_H -#define _ASM_IA64_SN_ACPI_H - -#include "acpi/acglobal.h" - -#define SN_ACPI_BASE_SUPPORT() (acpi_gbl_DSDT->oem_revision >= 0x20101) - -#endif /* _ASM_IA64_SN_ACPI_H */ diff --git a/include/asm-x86_64/acpi.h b/include/asm-x86_64/acpi.h index 6b6fc6f..49f92f3 100644 --- a/include/asm-x86_64/acpi.h +++ b/include/asm-x86_64/acpi.h @@ -57,11 +57,11 @@ int __acpi_acquire_global_lock(unsigned int *lock); int __acpi_release_global_lock(unsigned int *lock); -#define ACPI_ACQUIRE_GLOBAL_LOCK(GLptr, Acq) \ - ((Acq) = __acpi_acquire_global_lock((unsigned int *) GLptr)) +#define ACPI_ACQUIRE_GLOBAL_LOCK(facs, Acq) \ + ((Acq) = __acpi_acquire_global_lock(&facs->global_lock)) -#define ACPI_RELEASE_GLOBAL_LOCK(GLptr, Acq) \ - ((Acq) = __acpi_release_global_lock((unsigned int *) GLptr)) +#define ACPI_RELEASE_GLOBAL_LOCK(facs, Acq) \ + ((Acq) = __acpi_release_global_lock(&facs->global_lock)) /* * Math helper asm macros diff --git a/include/linux/acpi.h b/include/linux/acpi.h index 91f1f23..b3e8a26 100644 --- a/include/linux/acpi.h +++ b/include/linux/acpi.h @@ -53,57 +53,11 @@ enum acpi_irq_model_id { extern enum acpi_irq_model_id acpi_irq_model; - -/* Root System Description Pointer (RSDP) */ - -struct acpi_table_rsdp { - char signature[8]; - u8 checksum; - char oem_id[6]; - u8 revision; - u32 rsdt_address; -} __attribute__ ((packed)); - -struct acpi20_table_rsdp { - char signature[8]; - u8 checksum; - char oem_id[6]; - u8 revision; - u32 rsdt_address; - u32 length; - u64 xsdt_address; - u8 ext_checksum; - u8 reserved[3]; -} __attribute__ ((packed)); - typedef struct { u8 type; u8 length; } __attribute__ ((packed)) acpi_table_entry_header; -/* Root System Description Table (RSDT) */ - -struct acpi_table_rsdt { - struct acpi_table_header header; - u32 entry[8]; -} __attribute__ ((packed)); - -/* Extended System Description Table (XSDT) */ - -struct acpi_table_xsdt { - struct acpi_table_header header; - u64 entry[1]; -} __attribute__ ((packed)); - -/* Fixed ACPI Description Table (FADT) */ - -struct acpi_table_fadt { - struct acpi_table_header header; - u32 facs_addr; - u32 dsdt_addr; - /* ... */ -} __attribute__ ((packed)); - /* Multiple APIC Description Table (MADT) */ struct acpi_table_madt { -- cgit v0.10.2 From 2502fffb1958da66fa50a475081cb6827acdd9f3 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Add support for DMAR table Implement support for ACPI DMAR table (DMA Remapping Table) in header files and disassembler. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acdisasm.h b/include/acpi/acdisasm.h index 9a7d692..722583a 100644 --- a/include/acpi/acdisasm.h +++ b/include/acpi/acdisasm.h @@ -97,9 +97,10 @@ typedef const struct acpi_dmtable_info { #define ACPI_DMT_CHKSUM 20 #define ACPI_DMT_SPACEID 21 #define ACPI_DMT_GAS 22 -#define ACPI_DMT_MADT 23 -#define ACPI_DMT_SRAT 24 -#define ACPI_DMT_EXIT 25 +#define ACPI_DMT_DMAR 23 +#define ACPI_DMT_MADT 24 +#define ACPI_DMT_SRAT 25 +#define ACPI_DMT_EXIT 26 typedef void (*ACPI_TABLE_HANDLER) (struct acpi_table_header * table); @@ -147,6 +148,11 @@ extern struct acpi_dmtable_info acpi_dm_table_info_boot[]; extern struct acpi_dmtable_info acpi_dm_table_info_cpep[]; extern struct acpi_dmtable_info acpi_dm_table_info_cpep0[]; extern struct acpi_dmtable_info acpi_dm_table_info_dbgp[]; +extern struct acpi_dmtable_info acpi_dm_table_info_dmar[]; +extern struct acpi_dmtable_info acpi_dm_table_info_dmar_hdr[]; +extern struct acpi_dmtable_info acpi_dm_table_info_dmar_scope[]; +extern struct acpi_dmtable_info acpi_dm_table_info_dmar0[]; +extern struct acpi_dmtable_info acpi_dm_table_info_dmar1[]; extern struct acpi_dmtable_info acpi_dm_table_info_ecdt[]; extern struct acpi_dmtable_info acpi_dm_table_info_facs[]; extern struct acpi_dmtable_info acpi_dm_table_info_fadt1[]; @@ -201,6 +207,8 @@ void acpi_dm_dump_asf(struct acpi_table_header *table); void acpi_dm_dump_cpep(struct acpi_table_header *table); +void acpi_dm_dump_dmar(struct acpi_table_header *table); + void acpi_dm_dump_fadt(struct acpi_table_header *table); void acpi_dm_dump_srat(struct acpi_table_header *table); diff --git a/include/acpi/actbl1.h b/include/acpi/actbl1.h index 8ae30b7..515d82c 100644 --- a/include/acpi/actbl1.h +++ b/include/acpi/actbl1.h @@ -61,6 +61,7 @@ #define ACPI_SIG_BOOT "BOOT" /* Simple Boot Flag Table */ #define ACPI_SIG_CPEP "CPEP" /* Corrected Platform Error Polling table */ #define ACPI_SIG_DBGP "DBGP" /* Debug Port table */ +#define ACPI_SIG_DMAR "DMAR" /* DMA Remapping table */ #define ACPI_SIG_ECDT "ECDT" /* Embedded Controller Boot Resources Table */ #define ACPI_SIG_HPET "HPET" /* High Precision Event Timer table */ #define ACPI_SIG_MADT "APIC" /* Multiple APIC Description Table */ @@ -228,6 +229,78 @@ struct acpi_table_dbgp { /******************************************************************************* * + * DMAR - DMA Remapping table + * + ******************************************************************************/ + +struct acpi_table_dmar { + struct acpi_table_header header; /* Common ACPI table header */ + u8 width; /* Host Address Width */ + u8 reserved[11]; +}; + +/* DMAR subtable header */ + +struct acpi_dmar_header { + u16 type; + u16 length; + u8 flags; + u8 reserved[3]; +}; + +/* Values for subtable type in struct acpi_dmar_header */ + +enum acpi_dmar_type { + ACPI_DMAR_TYPE_HARDWARE_UNIT = 0, + ACPI_DMAR_TYPE_RESERVED_MEMORY = 1, + ACPI_DMAR_TYPE_RESERVED = 2 /* 2 and greater are reserved */ +}; + +struct acpi_dmar_device_scope { + u8 entry_type; + u8 length; + u8 segment; + u8 bus; +}; + +/* Values for entry_type in struct acpi_dmar_device_scope */ + +enum acpi_dmar_scope_type { + ACPI_DMAR_SCOPE_TYPE_NOT_USED = 0, + ACPI_DMAR_SCOPE_TYPE_ENDPOINT = 1, + ACPI_DMAR_SCOPE_TYPE_BRIDGE = 2, + ACPI_DMAR_SCOPE_TYPE_RESERVED = 3 /* 3 and greater are reserved */ +}; + +/* + * DMAR Sub-tables, correspond to Type in struct acpi_dmar_header + */ + +/* 0: Hardware Unit Definition */ + +struct acpi_dmar_hardware_unit { + struct acpi_dmar_header header; + u64 address; /* Register Base Address */ +}; + +/* Flags */ + +#define ACPI_DMAR_INCLUDE_ALL (1) + +/* 1: Reserved Memory Defininition */ + +struct acpi_dmar_reserved_memory { + struct acpi_dmar_header header; + u64 address; /* 4_k aligned base address */ + u64 end_address; /* 4_k aligned limit address */ +}; + +/* Flags */ + +#define ACPI_DMAR_ALLOW_ALL (1) + +/******************************************************************************* + * * ECDT - Embedded Controller Boot Resources Table * ******************************************************************************/ -- cgit v0.10.2 From fdffb72d23172c91af56983f303d1986994df522 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Add acpi_gpe_count global to track the number of GPE events Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evgpe.c b/drivers/acpi/events/evgpe.c index 1f98818..d9f71dd 100644 --- a/drivers/acpi/events/evgpe.c +++ b/drivers/acpi/events/evgpe.c @@ -618,6 +618,8 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) ACPI_FUNCTION_TRACE(ev_gpe_dispatch); + acpi_gpe_count++; + /* * If edge-triggered, clear the GPE status bit now. Note that * level-triggered events are cleared after the GPE is serviced. diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 8809306..a524e75 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -720,6 +720,7 @@ void acpi_ut_init_globals(void) /* GPE support */ + acpi_gpe_count = 0; acpi_gbl_gpe_xrupt_list_head = NULL; acpi_gbl_gpe_fadt_blocks[0] = NULL; acpi_gbl_gpe_fadt_blocks[1] = NULL; @@ -779,3 +780,4 @@ void acpi_ut_init_globals(void) ACPI_EXPORT_SYMBOL(acpi_dbg_level) ACPI_EXPORT_SYMBOL(acpi_dbg_layer) +ACPI_EXPORT_SYMBOL(acpi_gpe_count) diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index bd0fe7c..715c481 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -80,6 +80,10 @@ extern u32 acpi_dbg_layer; extern u32 acpi_gbl_nesting_level; +/* Event counters */ + +ACPI_EXTERN u32 acpi_gpe_count; + /* Support for dynamic control method tracing mechanism */ ACPI_EXTERN u32 acpi_gbl_original_dbg_level; -- cgit v0.10.2 From c5a7156959e89b32260ad6072bbf5077bcdfbeee Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Disable all wake GPEs after first one recieved Change for GPE support: when a wake GPE is received, now all wake GPEs are immediately disabled to prevent the waking GPE from firing again, and to prevent other wake GPEs from interrupting the wake process. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evgpe.c b/drivers/acpi/events/evgpe.c index d9f71dd..df92c9e 100644 --- a/drivers/acpi/events/evgpe.c +++ b/drivers/acpi/events/evgpe.c @@ -635,20 +635,23 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) } } - /* Save current system state */ - - if (acpi_gbl_system_awake_and_running) { - ACPI_SET_BIT(gpe_event_info->flags, ACPI_GPE_SYSTEM_RUNNING); - } else { - ACPI_CLEAR_BIT(gpe_event_info->flags, ACPI_GPE_SYSTEM_RUNNING); + if (!acpi_gbl_system_awake_and_running) { + /* + * We just woke up because of a wake GPE. Disable any further GPEs + * until we are fully up and running (Only wake GPEs should be enabled + * at this time, but we just brute-force disable them all.) + * 1) We must disable this particular wake GPE so it won't fire again + * 2) We want to disable all wake GPEs, since we are now awake + */ + (void)acpi_hw_disable_all_gpes(); } /* - * Dispatch the GPE to either an installed handler, or the control - * method associated with this GPE (_Lxx or _Exx). - * If a handler exists, we invoke it and do not attempt to run the method. - * If there is neither a handler nor a method, we disable the level to - * prevent further events from coming in here. + * Dispatch the GPE to either an installed handler, or the control method + * associated with this GPE (_Lxx or _Exx). If a handler exists, we invoke + * it and do not attempt to run the method. If there is neither a handler + * nor a method, we disable this GPE to prevent further such pointless + * events from firing. */ switch (gpe_event_info->flags & ACPI_GPE_DISPATCH_MASK) { case ACPI_GPE_DISPATCH_HANDLER: @@ -679,8 +682,8 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) case ACPI_GPE_DISPATCH_METHOD: /* - * Disable GPE, so it doesn't keep firing before the method has a - * chance to run. + * Disable the GPE, so it doesn't keep firing before the method has a + * chance to run (it runs asynchronously with interrupts enabled). */ status = acpi_ev_disable_gpe(gpe_event_info); if (ACPI_FAILURE(status)) { @@ -713,7 +716,7 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) gpe_number)); /* - * Disable the GPE. The GPE will remain disabled until the ACPI + * Disable the GPE. The GPE will remain disabled until the ACPI * Core Subsystem is restarted, or a handler is installed. */ status = acpi_ev_disable_gpe(gpe_event_info); @@ -728,50 +731,3 @@ acpi_ev_gpe_dispatch(struct acpi_gpe_event_info *gpe_event_info, u32 gpe_number) return_UINT32(ACPI_INTERRUPT_HANDLED); } - -#ifdef ACPI_GPE_NOTIFY_CHECK -/******************************************************************************* - * TBD: NOT USED, PROTOTYPE ONLY AND WILL PROBABLY BE REMOVED - * - * FUNCTION: acpi_ev_check_for_wake_only_gpe - * - * PARAMETERS: gpe_event_info - info for this GPE - * - * RETURN: Status - * - * DESCRIPTION: Determine if a a GPE is "wake-only". - * - * Called from Notify() code in interpreter when a "DeviceWake" - * Notify comes in. - * - ******************************************************************************/ - -acpi_status -acpi_ev_check_for_wake_only_gpe(struct acpi_gpe_event_info *gpe_event_info) -{ - acpi_status status; - - ACPI_FUNCTION_TRACE(ev_check_for_wake_only_gpe); - - if ((gpe_event_info) && /* Only >0 for _Lxx/_Exx */ - ((gpe_event_info->flags & ACPI_GPE_SYSTEM_MASK) == ACPI_GPE_SYSTEM_RUNNING)) { /* System state at GPE time */ - /* This must be a wake-only GPE, disable it */ - - status = acpi_ev_disable_gpe(gpe_event_info); - - /* Set GPE to wake-only. Do not change wake disabled/enabled status */ - - acpi_ev_set_gpe_type(gpe_event_info, ACPI_GPE_TYPE_WAKE); - - ACPI_INFO((AE_INFO, - "GPE %p was updated from wake/run to wake-only", - gpe_event_info)); - - /* This was a wake-only GPE */ - - return_ACPI_STATUS(AE_WAKE_ONLY_GPE); - } - - return_ACPI_STATUS(AE_OK); -} -#endif diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index 715c481..b74cd9b 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -58,41 +58,6 @@ #define ACPI_INIT_GLOBAL(a,b) a #endif -/* - * Keep local copies of these FADT-based registers. NOTE: These globals - * are first in this file for alignment reasons on 64-bit systems. - */ -ACPI_EXTERN struct acpi_generic_address acpi_gbl_xpm1a_enable; -ACPI_EXTERN struct acpi_generic_address acpi_gbl_xpm1b_enable; - -/***************************************************************************** - * - * Debug support - * - ****************************************************************************/ - -/* Runtime configuration of debug print levels */ - -extern u32 acpi_dbg_level; -extern u32 acpi_dbg_layer; - -/* Procedure nesting level for debug output */ - -extern u32 acpi_gbl_nesting_level; - -/* Event counters */ - -ACPI_EXTERN u32 acpi_gpe_count; - -/* Support for dynamic control method tracing mechanism */ - -ACPI_EXTERN u32 acpi_gbl_original_dbg_level; -ACPI_EXTERN u32 acpi_gbl_original_dbg_layer; -ACPI_EXTERN acpi_name acpi_gbl_trace_method_name; -ACPI_EXTERN u32 acpi_gbl_trace_dbg_level; -ACPI_EXTERN u32 acpi_gbl_trace_dbg_layer; -ACPI_EXTERN u32 acpi_gbl_trace_flags; - /***************************************************************************** * * Runtime configuration (static defaults that can be overriden at runtime) @@ -139,6 +104,34 @@ ACPI_EXTERN u8 ACPI_INIT_GLOBAL(acpi_gbl_leave_wake_gpes_disabled, TRUE); /***************************************************************************** * + * Debug support + * + ****************************************************************************/ + +/* Runtime configuration of debug print levels */ + +extern u32 acpi_dbg_level; +extern u32 acpi_dbg_layer; + +/* Procedure nesting level for debug output */ + +extern u32 acpi_gbl_nesting_level; + +/* Event counters */ + +ACPI_EXTERN u32 acpi_gpe_count; + +/* Support for dynamic control method tracing mechanism */ + +ACPI_EXTERN u32 acpi_gbl_original_dbg_level; +ACPI_EXTERN u32 acpi_gbl_original_dbg_layer; +ACPI_EXTERN acpi_name acpi_gbl_trace_method_name; +ACPI_EXTERN u32 acpi_gbl_trace_dbg_level; +ACPI_EXTERN u32 acpi_gbl_trace_dbg_layer; +ACPI_EXTERN u32 acpi_gbl_trace_flags; + +/***************************************************************************** + * * ACPI Table globals * ****************************************************************************/ @@ -154,6 +147,11 @@ ACPI_EXTERN struct acpi_table_fadt acpi_gbl_FADT; #define acpi_fadt acpi_gbl_FADT extern acpi_native_uint acpi_gbl_permanent_mmap; +/* These addresses are calculated from FADT address values */ + +ACPI_EXTERN struct acpi_generic_address acpi_gbl_xpm1a_enable; +ACPI_EXTERN struct acpi_generic_address acpi_gbl_xpm1b_enable; + /* * Handle both ACPI 1.0 and ACPI 2.0 Integer widths. The integer width is * determined by the revision of the DSDT: If the DSDT revision is less than diff --git a/include/acpi/actypes.h b/include/acpi/actypes.h index b0cdee6..fe9eb0e 100644 --- a/include/acpi/actypes.h +++ b/include/acpi/actypes.h @@ -592,7 +592,7 @@ typedef u32 acpi_event_status; * | | | +--- Type of dispatch -- to method, handler, or none * | | +--- Enabled for runtime? * | +--- Enabled for wake? - * +--- System state when GPE ocurred (running/waking) + * +--- Unused */ #define ACPI_GPE_XRUPT_TYPE_MASK (u8) 0x01 #define ACPI_GPE_LEVEL_TRIGGERED (u8) 0x01 @@ -618,10 +618,6 @@ typedef u32 acpi_event_status; #define ACPI_GPE_ENABLE_MASK (u8) 0x60 /* Both run/wake */ -#define ACPI_GPE_SYSTEM_MASK (u8) 0x80 -#define ACPI_GPE_SYSTEM_RUNNING (u8) 0x80 -#define ACPI_GPE_SYSTEM_WAKING (u8) 0x00 - /* * Flags for GPE and Lock interfaces */ -- cgit v0.10.2 From 3d81b236a82a26fa8bdef9096829675d81890dc9 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Fix unalignment in acpi_ut_repair_name Update interface to acpi_ut_repair_name() to avoid alignment issues on IA64 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/namespace/nsdump.c b/drivers/acpi/namespace/nsdump.c index d72df66..da88834 100644 --- a/drivers/acpi/namespace/nsdump.c +++ b/drivers/acpi/namespace/nsdump.c @@ -205,7 +205,7 @@ acpi_ns_dump_one_object(acpi_handle obj_handle, if (!acpi_ut_valid_acpi_name(this_node->name.integer)) { this_node->name.integer = - acpi_ut_repair_name(this_node->name.integer); + acpi_ut_repair_name(this_node->name.ascii); ACPI_WARNING((AE_INFO, "Invalid ACPI Name %08X", this_node->name.integer)); diff --git a/drivers/acpi/namespace/nssearch.c b/drivers/acpi/namespace/nssearch.c index 500e2bb..566f0a4 100644 --- a/drivers/acpi/namespace/nssearch.c +++ b/drivers/acpi/namespace/nssearch.c @@ -321,7 +321,8 @@ acpi_ns_search_and_enter(u32 target_name, * even though there are a few bad names. */ if (!acpi_ut_valid_acpi_name(target_name)) { - target_name = acpi_ut_repair_name(target_name); + target_name = + acpi_ut_repair_name(ACPI_CAST_PTR(char, &target_name)); /* Report warning only if in strict mode or debug mode */ diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index a524e75..855bc8f 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -566,7 +566,7 @@ char *acpi_ut_get_node_name(void *object) /* Name must be a valid ACPI name */ if (!acpi_ut_valid_acpi_name(node->name.integer)) { - node->name.integer = acpi_ut_repair_name(node->name.integer); + node->name.integer = acpi_ut_repair_name(node->name.ascii); } /* Return the name */ diff --git a/drivers/acpi/utilities/utmisc.c b/drivers/acpi/utilities/utmisc.c index 4b03051..36d8815 100644 --- a/drivers/acpi/utilities/utmisc.c +++ b/drivers/acpi/utilities/utmisc.c @@ -582,26 +582,25 @@ u8 acpi_ut_valid_acpi_name(u32 name) * ******************************************************************************/ -acpi_name acpi_ut_repair_name(acpi_name name) +acpi_name acpi_ut_repair_name(char *name) { - char *name_ptr = ACPI_CAST_PTR(char, &name); - char new_name[ACPI_NAME_SIZE]; acpi_native_uint i; + char new_name[ACPI_NAME_SIZE]; for (i = 0; i < ACPI_NAME_SIZE; i++) { - new_name[i] = name_ptr[i]; + new_name[i] = name[i]; /* * Replace a bad character with something printable, yet technically * still invalid. This prevents any collisions with existing "good" * names in the namespace. */ - if (!acpi_ut_valid_acpi_char(name_ptr[i], i)) { + if (!acpi_ut_valid_acpi_char(name[i], i)) { new_name[i] = '*'; } } - return (*ACPI_CAST_PTR(u32, new_name)); + return (*(u32 *) new_name); } /******************************************************************************* diff --git a/include/acpi/acutils.h b/include/acpi/acutils.h index ba039ea..beb07ac 100644 --- a/include/acpi/acutils.h +++ b/include/acpi/acutils.h @@ -470,7 +470,7 @@ void acpi_ut_print_string(char *string, u8 max_length); u8 acpi_ut_valid_acpi_name(u32 name); -acpi_name acpi_ut_repair_name(acpi_name name); +acpi_name acpi_ut_repair_name(char *name); u8 acpi_ut_valid_acpi_char(char character, acpi_native_uint position); -- cgit v0.10.2 From 69874165ab953a62f9adb3096ccd84ed2561a602 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Store GPE number instead of bitmask Update internal GPE data structure to simplify debug, use gpe_number instead of register bitmask. Signed-off-by: Bob Moore Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evgpe.c b/drivers/acpi/events/evgpe.c index df92c9e..35933be 100644 --- a/drivers/acpi/events/evgpe.c +++ b/drivers/acpi/events/evgpe.c @@ -121,7 +121,9 @@ acpi_ev_update_gpe_enable_masks(struct acpi_gpe_event_info *gpe_event_info, if (!gpe_register_info) { return_ACPI_STATUS(AE_NOT_EXIST); } - register_bit = gpe_event_info->register_bit; + register_bit = (u8) + (1 << + (gpe_event_info->gpe_number - gpe_register_info->base_gpe_number)); /* 1) Disable case. Simply clear all enable bits */ @@ -458,8 +460,7 @@ u32 acpi_ev_gpe_detect(struct acpi_gpe_xrupt_info * gpe_xrupt_list) /* Examine one GPE bit */ - if (enabled_status_byte & - acpi_gbl_decode_to8bit[j]) { + if (enabled_status_byte & (1 << j)) { /* * Found an active GPE. Dispatch the event to a handler * or method. diff --git a/drivers/acpi/events/evgpeblk.c b/drivers/acpi/events/evgpeblk.c index bb0eb50..8a6f01a 100644 --- a/drivers/acpi/events/evgpeblk.c +++ b/drivers/acpi/events/evgpeblk.c @@ -819,7 +819,8 @@ acpi_ev_create_gpe_info_blocks(struct acpi_gpe_block_info *gpe_block) /* Init the event_info for each GPE within this register */ for (j = 0; j < ACPI_GPE_REGISTER_WIDTH; j++) { - this_event->register_bit = acpi_gbl_decode_to8bit[j]; + this_event->gpe_number = + (u8) (this_register->base_gpe_number + j); this_event->register_info = this_register; this_event++; } diff --git a/drivers/acpi/hardware/hwgpe.c b/drivers/acpi/hardware/hwgpe.c index 608a3a6..3d548b5 100644 --- a/drivers/acpi/hardware/hwgpe.c +++ b/drivers/acpi/hardware/hwgpe.c @@ -105,14 +105,20 @@ acpi_hw_write_gpe_enable_reg(struct acpi_gpe_event_info *gpe_event_info) acpi_status acpi_hw_clear_gpe(struct acpi_gpe_event_info * gpe_event_info) { acpi_status status; + u8 register_bit; ACPI_FUNCTION_ENTRY(); + register_bit = (u8) + (1 << + (gpe_event_info->gpe_number - + gpe_event_info->register_info->base_gpe_number)); + /* * Write a one to the appropriate bit in the status register to * clear this GPE. */ - status = acpi_hw_low_level_write(8, gpe_event_info->register_bit, + status = acpi_hw_low_level_write(8, register_bit, &gpe_event_info->register_info-> status_address); @@ -155,7 +161,10 @@ acpi_hw_get_gpe_status(struct acpi_gpe_event_info * gpe_event_info, /* Get the register bitmask for this GPE */ - register_bit = gpe_event_info->register_bit; + register_bit = (u8) + (1 << + (gpe_event_info->gpe_number - + gpe_event_info->register_info->base_gpe_number)); /* GPE currently enabled? (enabled for runtime?) */ diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 855bc8f..5b83f86 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -164,8 +164,6 @@ u32 acpi_gbl_startup_flags = 0; u8 acpi_gbl_shutdown = TRUE; -const u8 acpi_gbl_decode_to8bit[8] = { 1, 2, 4, 8, 16, 32, 64, 128 }; - const char *acpi_gbl_sleep_state_names[ACPI_S_STATE_COUNT] = { "\\_S0_", "\\_S1_", diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index b74cd9b..0c2e1ae 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -240,7 +240,6 @@ ACPI_EXTERN u8 acpi_gbl_system_awake_and_running; extern u8 acpi_gbl_shutdown; extern u32 acpi_gbl_startup_flags; -extern const u8 acpi_gbl_decode_to8bit[8]; extern const char *acpi_gbl_sleep_state_names[ACPI_S_STATE_COUNT]; extern const char *acpi_gbl_highest_dstate_names[4]; extern const struct acpi_opcode_info acpi_gbl_aml_op_info[AML_NUM_OPCODES]; diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index a870484..553763d 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -367,7 +367,7 @@ struct acpi_gpe_event_info { union acpi_gpe_dispatch_info dispatch; /* Either Method or Handler */ struct acpi_gpe_register_info *register_info; /* Backpointer to register info */ u8 flags; /* Misc info about this GPE */ - u8 register_bit; /* This GPE bit within the register */ + u8 gpe_number; /* This GPE */ }; /* Information about a GPE register pair, one per each status/enable pair in an array */ -- cgit v0.10.2 From 84fb2c97731c1631c5548c15f3698ad82c274245 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:19 +0300 Subject: ACPICA: Split acpi_format_exception into two parts Split acpi_format_exception into two parts. New function is acpi_ut_verify_exception and will be used to verify exception codes returned by user. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 5b83f86..509a85d 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -52,87 +52,6 @@ ACPI_EXPORT_SYMBOL(acpi_gbl_FADT) /******************************************************************************* * - * FUNCTION: acpi_format_exception - * - * PARAMETERS: Status - The acpi_status code to be formatted - * - * RETURN: A string containing the exception text. A valid pointer is - * always returned. - * - * DESCRIPTION: This function translates an ACPI exception into an ASCII string. - * - ******************************************************************************/ -const char *acpi_format_exception(acpi_status status) -{ - acpi_status sub_status; - const char *exception = NULL; - - ACPI_FUNCTION_ENTRY(); - - /* - * Status is composed of two parts, a "type" and an actual code - */ - sub_status = (status & ~AE_CODE_MASK); - - switch (status & AE_CODE_MASK) { - case AE_CODE_ENVIRONMENTAL: - - if (sub_status <= AE_CODE_ENV_MAX) { - exception = acpi_gbl_exception_names_env[sub_status]; - } - break; - - case AE_CODE_PROGRAMMER: - - if (sub_status <= AE_CODE_PGM_MAX) { - exception = - acpi_gbl_exception_names_pgm[sub_status - 1]; - } - break; - - case AE_CODE_ACPI_TABLES: - - if (sub_status <= AE_CODE_TBL_MAX) { - exception = - acpi_gbl_exception_names_tbl[sub_status - 1]; - } - break; - - case AE_CODE_AML: - - if (sub_status <= AE_CODE_AML_MAX) { - exception = - acpi_gbl_exception_names_aml[sub_status - 1]; - } - break; - - case AE_CODE_CONTROL: - - if (sub_status <= AE_CODE_CTRL_MAX) { - exception = - acpi_gbl_exception_names_ctrl[sub_status - 1]; - } - break; - - default: - break; - } - - if (!exception) { - - /* Exception code was not recognized */ - - ACPI_ERROR((AE_INFO, - "Unknown exception code: 0x%8.8X", status)); - - exception = "UNKNOWN_STATUS_CODE"; - } - - return (ACPI_CAST_PTR(const char, exception)); -} - -/******************************************************************************* - * * Static global variable initialization. * ******************************************************************************/ @@ -182,10 +101,45 @@ const char *acpi_gbl_highest_dstate_names[4] = { /******************************************************************************* * - * Namespace globals + * FUNCTION: acpi_format_exception + * + * PARAMETERS: Status - The acpi_status code to be formatted + * + * RETURN: A string containing the exception text. A valid pointer is + * always returned. + * + * DESCRIPTION: This function translates an ACPI exception into an ASCII string + * It is here instead of utxface.c so it is always present. * ******************************************************************************/ +const char *acpi_format_exception(acpi_status status) +{ + const char *exception = NULL; + + ACPI_FUNCTION_ENTRY(); + + exception = acpi_ut_validate_exception(status); + if (!exception) { + + /* Exception code was not recognized */ + + ACPI_ERROR((AE_INFO, + "Unknown exception code: 0x%8.8X", status)); + + exception = "UNKNOWN_STATUS_CODE"; + } + + return (ACPI_CAST_PTR(const char, exception)); +} + +ACPI_EXPORT_SYMBOL(acpi_format_exception) + +/******************************************************************************* + * + * Namespace globals + * + ******************************************************************************/ /* * Predefined ACPI Names (Built-in to the Interpreter) * diff --git a/drivers/acpi/utilities/utmisc.c b/drivers/acpi/utilities/utmisc.c index 36d8815..e437bc7 100644 --- a/drivers/acpi/utilities/utmisc.c +++ b/drivers/acpi/utilities/utmisc.c @@ -51,6 +51,78 @@ ACPI_MODULE_NAME("utmisc") /******************************************************************************* * + * FUNCTION: acpi_ut_validate_exception + * + * PARAMETERS: Status - The acpi_status code to be formatted + * + * RETURN: A string containing the exception text. NULL if exception is + * not valid. + * + * DESCRIPTION: This function validates and translates an ACPI exception into + * an ASCII string. + * + ******************************************************************************/ +const char *acpi_ut_validate_exception(acpi_status status) +{ + acpi_status sub_status; + const char *exception = NULL; + + ACPI_FUNCTION_ENTRY(); + + /* + * Status is composed of two parts, a "type" and an actual code + */ + sub_status = (status & ~AE_CODE_MASK); + + switch (status & AE_CODE_MASK) { + case AE_CODE_ENVIRONMENTAL: + + if (sub_status <= AE_CODE_ENV_MAX) { + exception = acpi_gbl_exception_names_env[sub_status]; + } + break; + + case AE_CODE_PROGRAMMER: + + if (sub_status <= AE_CODE_PGM_MAX) { + exception = + acpi_gbl_exception_names_pgm[sub_status - 1]; + } + break; + + case AE_CODE_ACPI_TABLES: + + if (sub_status <= AE_CODE_TBL_MAX) { + exception = + acpi_gbl_exception_names_tbl[sub_status - 1]; + } + break; + + case AE_CODE_AML: + + if (sub_status <= AE_CODE_AML_MAX) { + exception = + acpi_gbl_exception_names_aml[sub_status - 1]; + } + break; + + case AE_CODE_CONTROL: + + if (sub_status <= AE_CODE_CTRL_MAX) { + exception = + acpi_gbl_exception_names_ctrl[sub_status - 1]; + } + break; + + default: + break; + } + + return (ACPI_CAST_PTR(const char, exception)); +} + +/******************************************************************************* + * * FUNCTION: acpi_ut_is_aml_table * * PARAMETERS: Table - An ACPI table @@ -62,6 +134,7 @@ ACPI_MODULE_NAME("utmisc") * data tables that do not contain AML code. * ******************************************************************************/ + u8 acpi_ut_is_aml_table(struct acpi_table_header *table) { diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index 0c2e1ae..8dab29a 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -245,6 +245,14 @@ extern const char *acpi_gbl_highest_dstate_names[4]; extern const struct acpi_opcode_info acpi_gbl_aml_op_info[AML_NUM_OPCODES]; extern const char *acpi_gbl_region_types[ACPI_NUM_PREDEFINED_REGIONS]; +/* Exception codes */ + +extern char const *acpi_gbl_exception_names_env[]; +extern char const *acpi_gbl_exception_names_pgm[]; +extern char const *acpi_gbl_exception_names_tbl[]; +extern char const *acpi_gbl_exception_names_aml[]; +extern char const *acpi_gbl_exception_names_ctrl[]; + /***************************************************************************** * * Namespace globals diff --git a/include/acpi/acutils.h b/include/acpi/acutils.h index beb07ac..3c66f54 100644 --- a/include/acpi/acutils.h +++ b/include/acpi/acutils.h @@ -453,6 +453,8 @@ acpi_ut_short_divide(acpi_integer in_dividend, /* * utmisc */ +const char *acpi_ut_validate_exception(acpi_status status); + u8 acpi_ut_is_aml_table(struct acpi_table_header *table); acpi_status acpi_ut_allocate_owner_id(acpi_owner_id * owner_id); -- cgit v0.10.2 From 0eaa14c02809cc93386b907846da5c024fd73012 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Update version to 20060831 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index 1fea8ae..4db7858 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20060828 +#define ACPI_CA_VERSION 0x20060831 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, @@ -158,8 +158,8 @@ /* Sizes for ACPI table headers */ -#define ACPI_OEM_ID_SIZE 6 -#define ACPI_OEM_TABLE_ID_SIZE 8 +#define ACPI_OEM_ID_SIZE 6 +#define ACPI_OEM_TABLE_ID_SIZE 8 /* Constants used in searching for the RSDP in low memory */ -- cgit v0.10.2 From b89b71a0019660d73e3c9671205c49e443d7085c Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Cleanup of FADT verification function. Removed offset display, not needed. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/utilities/utinit.c b/drivers/acpi/utilities/utinit.c index 2d2c4a3..5079f19 100644 --- a/drivers/acpi/utilities/utinit.c +++ b/drivers/acpi/utilities/utinit.c @@ -50,8 +50,7 @@ ACPI_MODULE_NAME("utinit") /* Local prototypes */ -static void -acpi_ut_fadt_register_error(char *register_name, u32 value, u8 offset); +static void acpi_ut_fadt_register_error(char *register_name, u32 value); static void acpi_ut_terminate(void); @@ -61,21 +60,18 @@ static void acpi_ut_terminate(void); * * PARAMETERS: register_name - Pointer to string identifying register * Value - Actual register contents value - * Offset - Byte offset in the FADT * - * RETURN: AE_BAD_VALUE + * RETURN: None * * DESCRIPTION: Display failure message * ******************************************************************************/ -static void -acpi_ut_fadt_register_error(char *register_name, u32 value, u8 offset) +static void acpi_ut_fadt_register_error(char *register_name, u32 value) { - ACPI_WARNING((AE_INFO, - "Invalid FADT value %s=%X at offset %X in FADT=%p", - register_name, value, offset, &acpi_gbl_FADT)); + ACPI_WARNING((AE_INFO, "Invalid FADT value %s = %X", + register_name, value)); } /****************************************************************************** @@ -98,69 +94,54 @@ acpi_status acpi_ut_validate_fadt(void) * but don't abort on any problems, just display error */ if (acpi_gbl_FADT.pm1_event_length < 4) { - acpi_ut_fadt_register_error("PM1_EVT_LEN", + acpi_ut_fadt_register_error("Pm1EventLength", (u32) acpi_gbl_FADT. - pm1_event_length, - ACPI_FADT_OFFSET(pm1_event_length)); + pm1_event_length); + } + + if (acpi_gbl_FADT.pm_timer_length < 4) { + acpi_ut_fadt_register_error("PmTimerLength", + (u32) acpi_gbl_FADT. + pm_timer_length); } if (!acpi_gbl_FADT.pm1_control_length) { - acpi_ut_fadt_register_error("PM1_CNT_LEN", 0, - ACPI_FADT_OFFSET - (pm1_control_length)); + acpi_ut_fadt_register_error("Pm1ControlLength", 0); } if (!acpi_gbl_FADT.xpm1a_event_block.address) { - acpi_ut_fadt_register_error("X_PM1a_EVT_BLK", 0, - ACPI_FADT_OFFSET(xpm1a_event_block. - address)); + acpi_ut_fadt_register_error("XPm1aEventBlock.Address", 0); } if (!acpi_gbl_FADT.xpm1a_control_block.address) { - acpi_ut_fadt_register_error("X_PM1a_CNT_BLK", 0, - ACPI_FADT_OFFSET - (xpm1a_control_block.address)); + acpi_ut_fadt_register_error("XPm1aControlBlock.Address", 0); } if (!acpi_gbl_FADT.xpm_timer_block.address) { - acpi_ut_fadt_register_error("X_PM_TMR_BLK", 0, - ACPI_FADT_OFFSET(xpm_timer_block. - address)); + acpi_ut_fadt_register_error("XPmTimerBlock.Address", 0); } if ((acpi_gbl_FADT.xpm2_control_block.address && !acpi_gbl_FADT.pm2_control_length)) { - acpi_ut_fadt_register_error("PM2_CNT_LEN", + acpi_ut_fadt_register_error("Pm2ControlLength", (u32) acpi_gbl_FADT. - pm2_control_length, - ACPI_FADT_OFFSET - (pm2_control_length)); - } - - if (acpi_gbl_FADT.pm_timer_length < 4) { - acpi_ut_fadt_register_error("PM_TM_LEN", - (u32) acpi_gbl_FADT.pm_timer_length, - ACPI_FADT_OFFSET(pm_timer_length)); + pm2_control_length); } /* Length of GPE blocks must be a multiple of 2 */ if (acpi_gbl_FADT.xgpe0_block.address && (acpi_gbl_FADT.gpe0_block_length & 1)) { - acpi_ut_fadt_register_error("(x)GPE0_BLK_LEN", + acpi_ut_fadt_register_error("Gpe0BlockLength", (u32) acpi_gbl_FADT. - gpe0_block_length, - ACPI_FADT_OFFSET - (gpe0_block_length)); + gpe0_block_length); } if (acpi_gbl_FADT.xgpe1_block.address && (acpi_gbl_FADT.gpe1_block_length & 1)) { - acpi_ut_fadt_register_error("(x)GPE1_BLK_LEN", + acpi_ut_fadt_register_error("Gpe1BlockLength", (u32) acpi_gbl_FADT. - gpe1_block_length, - ACPI_FADT_OFFSET - (gpe1_block_length)); + gpe1_block_length); } return (AE_OK); -- cgit v0.10.2 From 95befdb398e0112ede80529f6770644ecfa5a82e Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Create tbfadt.c to hold all FADT-related functions Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/Makefile b/drivers/acpi/tables/Makefile index f08f1f3..0a7d7af 100644 --- a/drivers/acpi/tables/Makefile +++ b/drivers/acpi/tables/Makefile @@ -2,6 +2,6 @@ # Makefile for all Linux ACPI interpreter subdirectories # -obj-y := tbxface.o tbinstal.o tbutils.o tbfind.o +obj-y := tbxface.o tbinstal.o tbutils.o tbfind.o tbfadt.o EXTRA_CFLAGS += $(ACPI_CFLAGS) diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c new file mode 100644 index 0000000..2336a72 --- /dev/null +++ b/drivers/acpi/tables/tbfadt.c @@ -0,0 +1,380 @@ +/****************************************************************************** + * + * Module Name: tbfadt - FADT table utilities + * + *****************************************************************************/ + +/* + * Copyright (C) 2000 - 2006, R. Byron Moore + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions, and the following disclaimer, + * without modification. + * 2. Redistributions in binary form must reproduce at minimum a disclaimer + * substantially similar to the "NO WARRANTY" disclaimer below + * ("Disclaimer") and any redistribution must be conditioned upon + * including a substantially similar Disclaimer requirement for further + * binary redistribution. + * 3. Neither the names of the above-listed copyright holders nor the names + * of any contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * Alternatively, this software may be distributed under the terms of the + * GNU General Public License ("GPL") version 2 as published by the Free + * Software Foundation. + * + * NO WARRANTY + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGES. + */ + +#include +#include + +#define _COMPONENT ACPI_TABLES +ACPI_MODULE_NAME("tbfadt") + +/* Local prototypes */ +static void inline +acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, + u8 bit_width, u64 address); + +static void acpi_tb_fadt_register_error(char *register_name, u32 value); + +static void acpi_tb_convert_fadt(void); + +static void acpi_tb_validate_fadt(void); + +/* Table used for conversion of FADT to common format */ + +typedef struct acpi_fadt_conversion { + u8 target; + u8 source; + u8 length; + +} acpi_fadt_conversion; + +static struct acpi_fadt_conversion fadt_conversion_table[] = { + {ACPI_FADT_OFFSET(xpm1a_event_block), + ACPI_FADT_OFFSET(pm1a_event_block), + ACPI_FADT_OFFSET(pm1_event_length)}, + {ACPI_FADT_OFFSET(xpm1b_event_block), + ACPI_FADT_OFFSET(pm1b_event_block), + ACPI_FADT_OFFSET(pm1_event_length)}, + {ACPI_FADT_OFFSET(xpm1a_control_block), + ACPI_FADT_OFFSET(pm1a_control_block), + ACPI_FADT_OFFSET(pm1_control_length)}, + {ACPI_FADT_OFFSET(xpm1b_control_block), + ACPI_FADT_OFFSET(pm1b_control_block), + ACPI_FADT_OFFSET(pm1_control_length)}, + {ACPI_FADT_OFFSET(xpm2_control_block), + ACPI_FADT_OFFSET(pm2_control_block), + ACPI_FADT_OFFSET(pm2_control_length)}, + {ACPI_FADT_OFFSET(xpm_timer_block), ACPI_FADT_OFFSET(pm_timer_block), + ACPI_FADT_OFFSET(pm_timer_length)}, + {ACPI_FADT_OFFSET(xgpe0_block), ACPI_FADT_OFFSET(gpe0_block), + ACPI_FADT_OFFSET(gpe0_block_length)}, + {ACPI_FADT_OFFSET(xgpe1_block), ACPI_FADT_OFFSET(gpe1_block), + ACPI_FADT_OFFSET(gpe1_block_length)} +}; + +#define ACPI_FADT_CONVERSION_ENTRIES (sizeof (fadt_conversion_table) / sizeof (struct acpi_fadt_conversion)) + +/******************************************************************************* + * + * FUNCTION: acpi_tb_init_generic_address + * + * PARAMETERS: new_gas_struct - GAS struct to be initialized + * bit_width - Width of this register + * Address - Address of the register + * + * RETURN: None + * + * DESCRIPTION: Initialize a GAS structure. + * + ******************************************************************************/ + +static void inline +acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, + u8 bit_width, u64 address) +{ + + ACPI_MOVE_64_TO_64(&new_gas_struct->address, &address); + new_gas_struct->space_id = ACPI_ADR_SPACE_SYSTEM_IO; + new_gas_struct->bit_width = bit_width; + new_gas_struct->bit_offset = 0; + new_gas_struct->access_width = 0; +} + +/******************************************************************************* + * + * FUNCTION: acpi_tb_parse_fadt + * + * PARAMETERS: table_index - Index for the FADT + * Flags - Flags + * + * RETURN: None + * + * DESCRIPTION: Initialize the FADT, DSDT and FACS tables + * (FADT contains the addresses of the DSDT and FACS) + * + ******************************************************************************/ + +void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) +{ + u32 length; + struct acpi_table_header *table; + + /* + * Special case for the FADT because of multiple versions and the fact + * that it contains pointers to both the DSDT and FACS tables. + * + * Get a local copy of the FADT and convert it to a common format + * Map entire FADT, assumed to be smaller than one page. + */ + length = acpi_gbl_root_table_list.tables[table_index].length; + + table = + acpi_os_map_memory(acpi_gbl_root_table_list.tables[table_index]. + address, length); + if (!table) { + return; + } + + /* + * Validate the FADT checksum before we copy the table. Ignore + * checksum error as we want to try to get the DSDT and FACS. + */ + (void)acpi_tb_verify_checksum(table, length); + + /* Copy the entire FADT locally */ + + ACPI_MEMSET(&acpi_gbl_FADT, 0, sizeof(struct acpi_table_fadt)); + + ACPI_MEMCPY(&acpi_gbl_FADT, table, + ACPI_MIN(length, sizeof(struct acpi_table_fadt))); + acpi_os_unmap_memory(table, length); + + /* Convert local FADT to the common internal format */ + + acpi_tb_convert_fadt(); + + /* Extract the DSDT and FACS tables from the FADT */ + + acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt, + flags, ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT); + + acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xfacs, + flags, ACPI_SIG_FACS, ACPI_TABLE_INDEX_FACS); + + /* Validate important FADT values */ + + acpi_tb_validate_fadt(); +} + +/******************************************************************************* + * + * FUNCTION: acpi_tb_convert_fadt + * + * PARAMETERS: None, uses acpi_gbl_FADT + * + * RETURN: None + * + * DESCRIPTION: Converts all versions of the FADT to a common internal format. + * + * NOTE: acpi_gbl_FADT must be of size (struct acpi_table_fadt), and must contain + * a copy of the actual FADT. + * + * ACPICA will use the "X" fields of the FADT for all addresses. + * + * "X" fields are optional extensions to the original V1.0 fields. Even if + * they are present in the structure, they can be optionally not used by + * setting them to zero. Therefore, we must selectively expand V1.0 fields + * if the corresponding X field is zero. + * + * For ACPI 1.0 FADTs, all address fields are expanded to the corresponding + * "X" fields. + * + * For ACPI 2.0 FADTs, any "X" fields that are NULL are filled in by + * expanding the corresponding ACPI 1.0 field. + * + ******************************************************************************/ + +static void acpi_tb_convert_fadt(void) +{ + u8 pm1_register_length; + struct acpi_generic_address *target; + acpi_native_uint i; + + /* Expand the FACS and DSDT addresses as necessary */ + + if (!acpi_gbl_FADT.Xfacs) { + acpi_gbl_FADT.Xfacs = (u64) acpi_gbl_FADT.facs; + } + + if (!acpi_gbl_FADT.Xdsdt) { + acpi_gbl_FADT.Xdsdt = (u64) acpi_gbl_FADT.dsdt; + } + + /* + * Expand the 32-bit V1.0 addresses to the 64-bit "X" generic address + * structures as necessary. + */ + for (i = 0; i < ACPI_FADT_CONVERSION_ENTRIES; i++) { + target = + ACPI_ADD_PTR(struct acpi_generic_address, &acpi_gbl_FADT, + fadt_conversion_table[i].target); + + /* Expand only if the X target is null */ + + if (!target->address) { + acpi_tb_init_generic_address(target, + *ACPI_ADD_PTR(u8, + &acpi_gbl_FADT, + fadt_conversion_table + [i].length), + (u64) * ACPI_ADD_PTR(u32, + &acpi_gbl_FADT, + fadt_conversion_table + [i]. + source)); + } + } + + /* + * Calculate separate GAS structs for the PM1 Enable registers. + * These addresses do not appear (directly) in the FADT, so it is + * useful to calculate them once, here. + * + * The PM event blocks are split into two register blocks, first is the + * PM Status Register block, followed immediately by the PM Enable Register + * block. Each is of length (pm1_event_length/2) + */ + pm1_register_length = (u8) ACPI_DIV_2(acpi_gbl_FADT.pm1_event_length); + + /* PM1A is required */ + + acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, + pm1_register_length, + (acpi_gbl_FADT.xpm1a_event_block.address + + pm1_register_length)); + + /* PM1B is optional; leave null if not present */ + + if (acpi_gbl_FADT.xpm1b_event_block.address) { + acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, + pm1_register_length, + (acpi_gbl_FADT.xpm1b_event_block. + address + pm1_register_length)); + } + + /* Global FADT is the new common V2.0 FADT */ + + acpi_gbl_FADT.header.length = sizeof(struct acpi_table_fadt); +} + +/****************************************************************************** + * + * FUNCTION: acpi_tb_validate_fadt + * + * PARAMETERS: None + * + * RETURN: Status + * + * DESCRIPTION: Validate various ACPI registers in the FADT + * + ******************************************************************************/ + +static void acpi_tb_validate_fadt(void) +{ + + /* These length fields have a minimum value */ + + if (acpi_gbl_FADT.pm1_event_length < 4) { + acpi_tb_fadt_register_error("Pm1EventLength", + (u32) acpi_gbl_FADT. + pm1_event_length); + } + + if (acpi_gbl_FADT.pm_timer_length < 4) { + acpi_tb_fadt_register_error("PmTimerLength", + (u32) acpi_gbl_FADT. + pm_timer_length); + } + + /* These length and address fields must be non-zero */ + + if (!acpi_gbl_FADT.pm1_control_length) { + acpi_tb_fadt_register_error("Pm1ControlLength", 0); + } + + if (!acpi_gbl_FADT.xpm1a_event_block.address) { + acpi_tb_fadt_register_error("XPm1aEventBlock.Address", 0); + } + + if (!acpi_gbl_FADT.xpm1a_control_block.address) { + acpi_tb_fadt_register_error("XPm1aControlBlock.Address", 0); + } + + if (!acpi_gbl_FADT.xpm_timer_block.address) { + acpi_tb_fadt_register_error("XPmTimerBlock.Address", 0); + } + + /* If PM2 block is present, must have non-zero length */ + + if ((acpi_gbl_FADT.xpm2_control_block.address && + !acpi_gbl_FADT.pm2_control_length)) { + acpi_tb_fadt_register_error("Pm2ControlLength", + (u32) acpi_gbl_FADT. + pm2_control_length); + } + + /* Length of any valid GPE blocks must be a multiple of 2 */ + + if (acpi_gbl_FADT.xgpe0_block.address && + (acpi_gbl_FADT.gpe0_block_length & 1)) { + acpi_tb_fadt_register_error("Gpe0BlockLength", + (u32) acpi_gbl_FADT. + gpe0_block_length); + } + + if (acpi_gbl_FADT.xgpe1_block.address && + (acpi_gbl_FADT.gpe1_block_length & 1)) { + acpi_tb_fadt_register_error("Gpe1BlockLength", + (u32) acpi_gbl_FADT. + gpe1_block_length); + } +} + +/******************************************************************************* + * + * FUNCTION: acpi_tb_fadt_register_error + * + * PARAMETERS: register_name - Pointer to string identifying register + * Value - Actual register contents value + * + * RETURN: None + * + * DESCRIPTION: Display FADT warning message + * + ******************************************************************************/ + +static void acpi_tb_fadt_register_error(char *register_name, u32 value) +{ + + ACPI_WARNING((AE_INFO, "Invalid FADT value \"%s\" = %X", + register_name, value)); +} -- cgit v0.10.2 From 1ba753acb372c2955a4843302e92e49ce82e2fea Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Re-implement interpreters' "serialized mode" Enhanced the implementation of the interpreters' serialized mode (boot with "acpi_serialize" to set acpi_glb_all_methods_serialized flag.) When this mode is specified, instead of creating a serialization semaphore per control method, the interpreter lock is simply no longer released before a blocking operation during control method execution. This effectively makes the AML Interpreter single-threaded. The overhead of a semaphore per-method is eliminated. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evregion.c b/drivers/acpi/events/evregion.c index 21caae0..ef45971 100644 --- a/drivers/acpi/events/evregion.c +++ b/drivers/acpi/events/evregion.c @@ -291,7 +291,6 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj, u32 bit_width, acpi_integer * value) { acpi_status status; - acpi_status status2; acpi_adr_space_handler handler; acpi_adr_space_setup region_setup; union acpi_operand_object *handler_desc; @@ -345,7 +344,7 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj, * setup will potentially execute control methods * (e.g., _REG method for this region) */ - acpi_ex_exit_interpreter(); + acpi_ex_relinquish_interpreter(); status = region_setup(region_obj, ACPI_REGION_ACTIVATE, handler_desc->address_space.context, @@ -353,10 +352,7 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj, /* Re-enter the interpreter */ - status2 = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } + acpi_ex_reacquire_interpreter(); /* Check for failure of the Region Setup */ @@ -409,7 +405,7 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj, * exit the interpreter because the handler *might* block -- we don't * know what it will do, so we can't hold the lock on the intepreter. */ - acpi_ex_exit_interpreter(); + acpi_ex_relinquish_interpreter(); } /* Call the handler */ @@ -430,10 +426,7 @@ acpi_ev_address_space_dispatch(union acpi_operand_object *region_obj, * We just returned from a non-default handler, we must re-enter the * interpreter */ - status2 = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } + acpi_ex_reacquire_interpreter(); } return_ACPI_STATUS(status); diff --git a/drivers/acpi/events/evxface.c b/drivers/acpi/events/evxface.c index 923fd2b..a2af48e 100644 --- a/drivers/acpi/events/evxface.c +++ b/drivers/acpi/events/evxface.c @@ -768,11 +768,9 @@ acpi_status acpi_acquire_global_lock(u16 timeout, u32 * handle) return (AE_BAD_PARAMETER); } - status = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status)) { - return (status); - } + /* Must lock interpreter to prevent race conditions */ + acpi_ex_enter_interpreter(); status = acpi_ev_acquire_global_lock(timeout); acpi_ex_exit_interpreter(); diff --git a/drivers/acpi/executer/excreate.c b/drivers/acpi/executer/excreate.c index a4d29b2..c665aa7 100644 --- a/drivers/acpi/executer/excreate.c +++ b/drivers/acpi/executer/excreate.c @@ -583,10 +583,7 @@ acpi_ex_create_method(u8 * aml_start, * Get the sync_level. If method is serialized, a mutex will be * created for this method when it is parsed. */ - if (acpi_gbl_all_methods_serialized) { - obj_desc->method.sync_level = 0; - obj_desc->method.method_flags |= AML_METHOD_SERIALIZED; - } else if (method_flags & AML_METHOD_SERIALIZED) { + if (method_flags & AML_METHOD_SERIALIZED) { /* * ACPI 1.0: sync_level = 0 * ACPI 2.0: sync_level = sync_level in method declaration diff --git a/drivers/acpi/executer/exsystem.c b/drivers/acpi/executer/exsystem.c index 3b9736a..7e5aeb1 100644 --- a/drivers/acpi/executer/exsystem.c +++ b/drivers/acpi/executer/exsystem.c @@ -66,7 +66,6 @@ ACPI_MODULE_NAME("exsystem") acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout) { acpi_status status; - acpi_status status2; ACPI_FUNCTION_TRACE(ex_system_wait_semaphore); @@ -79,7 +78,7 @@ acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout) /* We must wait, so unlock the interpreter */ - acpi_ex_exit_interpreter(); + acpi_ex_relinquish_interpreter(); status = acpi_os_wait_semaphore(semaphore, 1, timeout); @@ -89,13 +88,7 @@ acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout) /* Reacquire the interpreter */ - status2 = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status2)) { - - /* Report fatal error, could not acquire interpreter */ - - return_ACPI_STATUS(status2); - } + acpi_ex_reacquire_interpreter(); } return_ACPI_STATUS(status); @@ -119,7 +112,6 @@ acpi_status acpi_ex_system_wait_semaphore(acpi_semaphore semaphore, u16 timeout) acpi_status acpi_ex_system_wait_mutex(acpi_mutex mutex, u16 timeout) { acpi_status status; - acpi_status status2; ACPI_FUNCTION_TRACE(ex_system_wait_mutex); @@ -132,7 +124,7 @@ acpi_status acpi_ex_system_wait_mutex(acpi_mutex mutex, u16 timeout) /* We must wait, so unlock the interpreter */ - acpi_ex_exit_interpreter(); + acpi_ex_relinquish_interpreter(); status = acpi_os_acquire_mutex(mutex, timeout); @@ -142,13 +134,7 @@ acpi_status acpi_ex_system_wait_mutex(acpi_mutex mutex, u16 timeout) /* Reacquire the interpreter */ - status2 = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status2)) { - - /* Report fatal error, could not acquire interpreter */ - - return_ACPI_STATUS(status2); - } + acpi_ex_reacquire_interpreter(); } return_ACPI_STATUS(status); @@ -209,20 +195,18 @@ acpi_status acpi_ex_system_do_stall(u32 how_long) acpi_status acpi_ex_system_do_suspend(acpi_integer how_long) { - acpi_status status; - ACPI_FUNCTION_ENTRY(); /* Since this thread will sleep, we must release the interpreter */ - acpi_ex_exit_interpreter(); + acpi_ex_relinquish_interpreter(); acpi_os_sleep(how_long); /* And now we must get the interpreter again */ - status = acpi_ex_enter_interpreter(); - return (status); + acpi_ex_reacquire_interpreter(); + return (AE_OK); } /******************************************************************************* diff --git a/drivers/acpi/executer/exutils.c b/drivers/acpi/executer/exutils.c index 982c8b6..72adcf4 100644 --- a/drivers/acpi/executer/exutils.c +++ b/drivers/acpi/executer/exutils.c @@ -76,46 +76,72 @@ static u32 acpi_ex_digits_needed(acpi_integer value, u32 base); * * PARAMETERS: None * - * RETURN: Status + * RETURN: None * - * DESCRIPTION: Enter the interpreter execution region. Failure to enter - * the interpreter region is a fatal system error + * DESCRIPTION: Enter the interpreter execution region. Failure to enter + * the interpreter region is a fatal system error. Used in + * conjunction with exit_interpreter. * ******************************************************************************/ -acpi_status acpi_ex_enter_interpreter(void) +void acpi_ex_enter_interpreter(void) { acpi_status status; - ACPI_FUNCTION_TRACE(ex_enter_interpreter); + ACPI_FUNCTION_TRACE(ex_reacquire_interpreter); status = acpi_ut_acquire_mutex(ACPI_MTX_INTERPRETER); if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, "Could not acquire interpreter mutex")); + ACPI_ERROR((AE_INFO, + "Could not acquire AML Interpreter mutex")); } - return_ACPI_STATUS(status); + return_VOID; } /******************************************************************************* * - * FUNCTION: acpi_ex_exit_interpreter + * FUNCTION: acpi_ex_reacquire_interpreter * * PARAMETERS: None * * RETURN: None * - * DESCRIPTION: Exit the interpreter execution region + * DESCRIPTION: Reacquire the interpreter execution region from within the + * interpreter code. Failure to enter the interpreter region is a + * fatal system error. Used in conjuction with + * relinquish_interpreter + * + ******************************************************************************/ + +void acpi_ex_reacquire_interpreter(void) +{ + + ACPI_FUNCTION_TRACE(ex_reacquire_interpreter); + + /* + * If the global serialized flag is set, do not release the interpreter, + * since it was not actually released by acpi_ex_relinquish_interpreter. + * This forces the interpreter to be single threaded. + */ + if (!acpi_gbl_all_methods_serialized) { + acpi_ex_enter_interpreter(); + } + + return_VOID; +} + +/******************************************************************************* + * + * FUNCTION: acpi_ex_exit_interpreter + * + * PARAMETERS: None + * + * RETURN: None * - * Cases where the interpreter is unlocked: - * 1) Completion of the execution of a control method - * 2) Method blocked on a Sleep() AML opcode - * 3) Method blocked on an Acquire() AML opcode - * 4) Method blocked on a Wait() AML opcode - * 5) Method blocked to acquire the global lock - * 6) Method blocked to execute a serialized control method that is - * already executing - * 7) About to invoke a user-installed opregion handler + * DESCRIPTION: Exit the interpreter execution region. This is the top level + * routine used to exit the interpreter when all processing has + * been completed. * ******************************************************************************/ @@ -127,7 +153,47 @@ void acpi_ex_exit_interpreter(void) status = acpi_ut_release_mutex(ACPI_MTX_INTERPRETER); if (ACPI_FAILURE(status)) { - ACPI_ERROR((AE_INFO, "Could not release interpreter mutex")); + ACPI_ERROR((AE_INFO, + "Could not release AML Interpreter mutex")); + } + + return_VOID; +} + +/******************************************************************************* + * + * FUNCTION: acpi_ex_relinquish_interpreter + * + * PARAMETERS: None + * + * RETURN: None + * + * DESCRIPTION: Exit the interpreter execution region, from within the + * interpreter - before attempting an operation that will possibly + * block the running thread. + * + * Cases where the interpreter is unlocked internally + * 1) Method to be blocked on a Sleep() AML opcode + * 2) Method to be blocked on an Acquire() AML opcode + * 3) Method to be blocked on a Wait() AML opcode + * 4) Method to be blocked to acquire the global lock + * 5) Method to be blocked waiting to execute a serialized control method + * that is currently executing + * 6) About to invoke a user-installed opregion handler + * + ******************************************************************************/ + +void acpi_ex_relinquish_interpreter(void) +{ + + ACPI_FUNCTION_TRACE(ex_relinquish_interpreter); + + /* + * If the global serialized flag is set, do not release the interpreter. + * This forces the interpreter to be single threaded. + */ + if (!acpi_gbl_all_methods_serialized) { + acpi_ex_exit_interpreter(); } return_VOID; @@ -141,8 +207,8 @@ void acpi_ex_exit_interpreter(void) * * RETURN: none * - * DESCRIPTION: Truncate a number to 32-bits if the currently executing method - * belongs to a 32-bit ACPI table. + * DESCRIPTION: Truncate an ACPI Integer to 32 bits if the execution mode is + * 32-bit, as determined by the revision of the DSDT. * ******************************************************************************/ diff --git a/drivers/acpi/namespace/nseval.c b/drivers/acpi/namespace/nseval.c index 4b0a4a8..7156616 100644 --- a/drivers/acpi/namespace/nseval.c +++ b/drivers/acpi/namespace/nseval.c @@ -154,11 +154,7 @@ acpi_status acpi_ns_evaluate(struct acpi_evaluate_info *info) * Execute the method via the interpreter. The interpreter is locked * here before calling into the AML parser */ - status = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - + acpi_ex_enter_interpreter(); status = acpi_ps_execute_method(info); acpi_ex_exit_interpreter(); } else { @@ -182,10 +178,7 @@ acpi_status acpi_ns_evaluate(struct acpi_evaluate_info *info) * resolution, we must lock it because we could access an opregion. * The opregion access code assumes that the interpreter is locked. */ - status = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } + acpi_ex_enter_interpreter(); /* Function has a strange interface */ diff --git a/drivers/acpi/namespace/nsinit.c b/drivers/acpi/namespace/nsinit.c index aec8488..0d3a42b 100644 --- a/drivers/acpi/namespace/nsinit.c +++ b/drivers/acpi/namespace/nsinit.c @@ -213,7 +213,7 @@ acpi_ns_init_one_object(acpi_handle obj_handle, u32 level, void *context, void **return_value) { acpi_object_type type; - acpi_status status; + acpi_status status = AE_OK; struct acpi_init_walk_info *info = (struct acpi_init_walk_info *)context; struct acpi_namespace_node *node = @@ -267,10 +267,7 @@ acpi_ns_init_one_object(acpi_handle obj_handle, /* * Must lock the interpreter before executing AML code */ - status = acpi_ex_enter_interpreter(); - if (ACPI_FAILURE(status)) { - return (status); - } + acpi_ex_enter_interpreter(); /* * Each of these types can contain executable AML code within the diff --git a/drivers/acpi/namespace/nsxfeval.c b/drivers/acpi/namespace/nsxfeval.c index dca6799..6a0a46e 100644 --- a/drivers/acpi/namespace/nsxfeval.c +++ b/drivers/acpi/namespace/nsxfeval.c @@ -170,7 +170,6 @@ acpi_evaluate_object(acpi_handle handle, struct acpi_buffer *return_buffer) { acpi_status status; - acpi_status status2; struct acpi_evaluate_info *info; acpi_size buffer_space_needed; u32 i; @@ -329,14 +328,12 @@ acpi_evaluate_object(acpi_handle handle, * Delete the internal return object. NOTE: Interpreter must be * locked to avoid race condition. */ - status2 = acpi_ex_enter_interpreter(); - if (ACPI_SUCCESS(status2)) { + acpi_ex_enter_interpreter(); - /* Remove one reference on the return object (should delete it) */ + /* Remove one reference on the return object (should delete it) */ - acpi_ut_remove_reference(info->return_object); - acpi_ex_exit_interpreter(); - } + acpi_ut_remove_reference(info->return_object); + acpi_ex_exit_interpreter(); } cleanup: diff --git a/include/acpi/acinterp.h b/include/acpi/acinterp.h index f266b38..8aebe57 100644 --- a/include/acpi/acinterp.h +++ b/include/acpi/acinterp.h @@ -445,10 +445,14 @@ acpi_ex_copy_integer_to_buffer_field(union acpi_operand_object *source_desc, /* * exutils - interpreter/scanner utilities */ -acpi_status acpi_ex_enter_interpreter(void); +void acpi_ex_enter_interpreter(void); void acpi_ex_exit_interpreter(void); +void acpi_ex_reacquire_interpreter(void); + +void acpi_ex_relinquish_interpreter(void); + void acpi_ex_truncate_for32bit_table(union acpi_operand_object *obj_desc); u8 acpi_ex_acquire_global_lock(u32 rule); -- cgit v0.10.2 From 765ec20180fb70b4ee9d730167b2a0b76879f791 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Delete stale FADT functions outside tbfadt.c. Moved all FADT-related functions to a new file, tbfadt.c. Eliminated the acpi_hw_initialize function - the FADT registers are now validated when the table is loaded. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/hardware/hwacpi.c b/drivers/acpi/hardware/hwacpi.c index 14e8111..9c7df71 100644 --- a/drivers/acpi/hardware/hwacpi.c +++ b/drivers/acpi/hardware/hwacpi.c @@ -49,34 +49,6 @@ ACPI_MODULE_NAME("hwacpi") /****************************************************************************** * - * FUNCTION: acpi_hw_initialize - * - * PARAMETERS: None - * - * RETURN: Status - * - * DESCRIPTION: Initialize and validate the various ACPI registers defined in - * the FADT. - * - ******************************************************************************/ -acpi_status acpi_hw_initialize(void) -{ - acpi_status status; - - ACPI_FUNCTION_TRACE(hw_initialize); - - /* Sanity check the FADT for valid values */ - - status = acpi_ut_validate_fadt(); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - return_ACPI_STATUS(AE_OK); -} - -/****************************************************************************** - * * FUNCTION: acpi_hw_set_mode * * PARAMETERS: Mode - SYS_MODE_ACPI or SYS_MODE_LEGACY @@ -86,7 +58,6 @@ acpi_status acpi_hw_initialize(void) * DESCRIPTION: Transitions the system into the requested mode. * ******************************************************************************/ - acpi_status acpi_hw_set_mode(u32 mode) { diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 6d13737..54e53e6 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -48,57 +48,10 @@ ACPI_MODULE_NAME("tbutils") /* Local prototypes */ -static void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags); - -static void acpi_tb_convert_fadt(void); - -static void -acpi_tb_install_table(acpi_physical_address address, - u8 flags, char *signature, acpi_native_uint table_index); - -static void inline -acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, - u8 bit_width, u64 address); - static acpi_physical_address acpi_tb_get_root_table_entry(u8 * table_entry, acpi_native_uint table_entry_size); -/* Table used for conversion of FADT to common format */ - -typedef struct acpi_fadt_conversion { - u8 target; - u8 source; - u8 length; - -} acpi_fadt_conversion; - -static struct acpi_fadt_conversion fadt_conversion_table[] = { - {ACPI_FADT_OFFSET(xpm1a_event_block), - ACPI_FADT_OFFSET(pm1a_event_block), - ACPI_FADT_OFFSET(pm1_event_length)}, - {ACPI_FADT_OFFSET(xpm1b_event_block), - ACPI_FADT_OFFSET(pm1b_event_block), - ACPI_FADT_OFFSET(pm1_event_length)}, - {ACPI_FADT_OFFSET(xpm1a_control_block), - ACPI_FADT_OFFSET(pm1a_control_block), - ACPI_FADT_OFFSET(pm1_control_length)}, - {ACPI_FADT_OFFSET(xpm1b_control_block), - ACPI_FADT_OFFSET(pm1b_control_block), - ACPI_FADT_OFFSET(pm1_control_length)}, - {ACPI_FADT_OFFSET(xpm2_control_block), - ACPI_FADT_OFFSET(pm2_control_block), - ACPI_FADT_OFFSET(pm2_control_length)}, - {ACPI_FADT_OFFSET(xpm_timer_block), ACPI_FADT_OFFSET(pm_timer_block), - ACPI_FADT_OFFSET(pm_timer_length)}, - {ACPI_FADT_OFFSET(xgpe0_block), ACPI_FADT_OFFSET(gpe0_block), - ACPI_FADT_OFFSET(gpe0_block_length)}, - {ACPI_FADT_OFFSET(xgpe1_block), ACPI_FADT_OFFSET(gpe1_block), - ACPI_FADT_OFFSET(gpe1_block_length)} -}; - -#define ACPI_FADT_CONVERSION_ENTRIES (sizeof (fadt_conversion_table) / sizeof (struct acpi_fadt_conversion)) - /******************************************************************************* * * FUNCTION: acpi_tb_print_table_header @@ -153,32 +106,6 @@ acpi_tb_print_table_header(acpi_physical_address address, /******************************************************************************* * - * FUNCTION: acpi_tb_init_generic_address - * - * PARAMETERS: new_gas_struct - GAS struct to be initialized - * bit_width - Width of this register - * Address - Address of the register - * - * RETURN: None - * - * DESCRIPTION: Initialize a GAS structure. - * - ******************************************************************************/ - -static void inline -acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, - u8 bit_width, u64 address) -{ - - ACPI_MOVE_64_TO_64(&new_gas_struct->address, &address); - new_gas_struct->space_id = ACPI_ADR_SPACE_SYSTEM_IO; - new_gas_struct->bit_width = bit_width; - new_gas_struct->bit_offset = 0; - new_gas_struct->access_width = 0; -} - -/******************************************************************************* - * * FUNCTION: acpi_tb_validate_checksum * * PARAMETERS: Table - ACPI table to verify @@ -243,107 +170,6 @@ u8 acpi_tb_checksum(u8 * buffer, acpi_native_uint length) /******************************************************************************* * - * FUNCTION: acpi_tb_convert_fadt - * - * PARAMETERS: None, uses acpi_gbl_FADT - * - * RETURN: None - * - * DESCRIPTION: Converts all versions of the FADT to a common internal format. - * - * NOTE: acpi_gbl_FADT must be of size (struct acpi_table_fadt), and must contain - * a copy of the actual FADT. - * - * ACPICA will use the "X" fields of the FADT for all addresses. - * - * "X" fields are optional extensions to the original V1.0 fields. Even if - * they are present in the structure, they can be optionally not used by - * setting them to zero. Therefore, we must selectively expand V1.0 fields - * if the corresponding X field is zero. - * - * For ACPI 1.0 FADTs, all address fields are expanded to the corresponding - * "X" fields. - * - * For ACPI 2.0 FADTs, any "X" fields that are NULL are filled in by - * expanding the corresponding ACPI 1.0 field. - * - ******************************************************************************/ - -static void acpi_tb_convert_fadt(void) -{ - u8 pm1_register_length; - struct acpi_generic_address *target; - acpi_native_uint i; - - /* Expand the FACS and DSDT addresses as necessary */ - - if (!acpi_gbl_FADT.Xfacs) { - acpi_gbl_FADT.Xfacs = (u64) acpi_gbl_FADT.facs; - } - - if (!acpi_gbl_FADT.Xdsdt) { - acpi_gbl_FADT.Xdsdt = (u64) acpi_gbl_FADT.dsdt; - } - - /* - * Expand the 32-bit V1.0 addresses to the 64-bit "X" generic address - * structures as necessary. - */ - for (i = 0; i < ACPI_FADT_CONVERSION_ENTRIES; i++) { - target = - ACPI_ADD_PTR(struct acpi_generic_address, &acpi_gbl_FADT, - fadt_conversion_table[i].target); - - /* Expand only if the X target is null */ - - if (!target->address) { - acpi_tb_init_generic_address(target, - *ACPI_ADD_PTR(u8, - &acpi_gbl_FADT, - fadt_conversion_table - [i].length), - (u64) * ACPI_ADD_PTR(u32, - &acpi_gbl_FADT, - fadt_conversion_table - [i]. - source)); - } - } - - /* - * Calculate separate GAS structs for the PM1 Enable registers. - * These addresses do not appear (directly) in the FADT, so it is - * useful to calculate them once, here. - * - * The PM event blocks are split into two register blocks, first is the - * PM Status Register block, followed immediately by the PM Enable Register - * block. Each is of length (pm1_event_length/2) - */ - pm1_register_length = (u8) ACPI_DIV_2(acpi_gbl_FADT.pm1_event_length); - - /* PM1A is required */ - - acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, - pm1_register_length, - (acpi_gbl_FADT.xpm1a_event_block.address + - pm1_register_length)); - - /* PM1B is optional; leave null if not present */ - - if (acpi_gbl_FADT.xpm1b_event_block.address) { - acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, - pm1_register_length, - (acpi_gbl_FADT.xpm1b_event_block. - address + pm1_register_length)); - } - - /* Global FADT is the new common V2.0 FADT */ - - acpi_gbl_FADT.header.length = sizeof(struct acpi_table_fadt); -} - -/******************************************************************************* - * * FUNCTION: acpi_tb_install_table * * PARAMETERS: Address - Physical address of DSDT or FACS @@ -358,7 +184,7 @@ static void acpi_tb_convert_fadt(void) * ******************************************************************************/ -static void +void acpi_tb_install_table(acpi_physical_address address, u8 flags, char *signature, acpi_native_uint table_index) { @@ -412,68 +238,6 @@ acpi_tb_install_table(acpi_physical_address address, /******************************************************************************* * - * FUNCTION: acpi_tb_parse_fadt - * - * PARAMETERS: table_index - Index for the FADT - * Flags - Flags - * - * RETURN: None - * - * DESCRIPTION: Initialize the FADT, DSDT and FACS tables - * (FADT contains the addresses of the DSDT and FACS) - * - ******************************************************************************/ - -static void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) -{ - u32 length; - struct acpi_table_header *table; - - /* - * Special case for the FADT because of multiple versions and the fact - * that it contains pointers to both the DSDT and FACS tables. - * - * Get a local copy of the FADT and convert it to a common format - * Map entire FADT, assumed to be smaller than one page. - */ - length = acpi_gbl_root_table_list.tables[table_index].length; - - table = - acpi_os_map_memory(acpi_gbl_root_table_list.tables[table_index]. - address, length); - if (!table) { - return; - } - - /* - * Validate the FADT checksum before we copy the table. Ignore - * checksum error as we want to try to get the DSDT and FACS. - */ - (void)acpi_tb_verify_checksum(table, length); - - /* Copy the entire FADT locally */ - - ACPI_MEMSET(&acpi_gbl_FADT, 0, sizeof(struct acpi_table_fadt)); - - ACPI_MEMCPY(&acpi_gbl_FADT, table, - ACPI_MIN(length, sizeof(struct acpi_table_fadt))); - acpi_os_unmap_memory(table, length); - - /* Convert local FADT to the common internal format */ - - acpi_tb_convert_fadt(); - - /* Extract the DSDT and FACS tables from the FADT */ - - acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt, - flags, ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT); - - acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xfacs, - flags, ACPI_SIG_FACS, ACPI_TABLE_INDEX_FACS); -} - -/******************************************************************************* - * * FUNCTION: acpi_tb_get_root_table_entry * * PARAMETERS: table_entry - Pointer to the RSDT/XSDT table entry diff --git a/drivers/acpi/utilities/utinit.c b/drivers/acpi/utilities/utinit.c index 5079f19..303bde70 100644 --- a/drivers/acpi/utilities/utinit.c +++ b/drivers/acpi/utilities/utinit.c @@ -50,103 +50,8 @@ ACPI_MODULE_NAME("utinit") /* Local prototypes */ -static void acpi_ut_fadt_register_error(char *register_name, u32 value); - static void acpi_ut_terminate(void); -/******************************************************************************* - * - * FUNCTION: acpi_ut_fadt_register_error - * - * PARAMETERS: register_name - Pointer to string identifying register - * Value - Actual register contents value - * - * RETURN: None - * - * DESCRIPTION: Display failure message - * - ******************************************************************************/ - -static void acpi_ut_fadt_register_error(char *register_name, u32 value) -{ - - ACPI_WARNING((AE_INFO, "Invalid FADT value %s = %X", - register_name, value)); -} - -/****************************************************************************** - * - * FUNCTION: acpi_ut_validate_fadt - * - * PARAMETERS: None - * - * RETURN: Status - * - * DESCRIPTION: Validate various ACPI registers in the FADT - * - ******************************************************************************/ - -acpi_status acpi_ut_validate_fadt(void) -{ - - /* - * Verify Fixed ACPI Description Table fields, - * but don't abort on any problems, just display error - */ - if (acpi_gbl_FADT.pm1_event_length < 4) { - acpi_ut_fadt_register_error("Pm1EventLength", - (u32) acpi_gbl_FADT. - pm1_event_length); - } - - if (acpi_gbl_FADT.pm_timer_length < 4) { - acpi_ut_fadt_register_error("PmTimerLength", - (u32) acpi_gbl_FADT. - pm_timer_length); - } - - if (!acpi_gbl_FADT.pm1_control_length) { - acpi_ut_fadt_register_error("Pm1ControlLength", 0); - } - - if (!acpi_gbl_FADT.xpm1a_event_block.address) { - acpi_ut_fadt_register_error("XPm1aEventBlock.Address", 0); - } - - if (!acpi_gbl_FADT.xpm1a_control_block.address) { - acpi_ut_fadt_register_error("XPm1aControlBlock.Address", 0); - } - - if (!acpi_gbl_FADT.xpm_timer_block.address) { - acpi_ut_fadt_register_error("XPmTimerBlock.Address", 0); - } - - if ((acpi_gbl_FADT.xpm2_control_block.address && - !acpi_gbl_FADT.pm2_control_length)) { - acpi_ut_fadt_register_error("Pm2ControlLength", - (u32) acpi_gbl_FADT. - pm2_control_length); - } - - /* Length of GPE blocks must be a multiple of 2 */ - - if (acpi_gbl_FADT.xgpe0_block.address && - (acpi_gbl_FADT.gpe0_block_length & 1)) { - acpi_ut_fadt_register_error("Gpe0BlockLength", - (u32) acpi_gbl_FADT. - gpe0_block_length); - } - - if (acpi_gbl_FADT.xgpe1_block.address && - (acpi_gbl_FADT.gpe1_block_length & 1)) { - acpi_ut_fadt_register_error("Gpe1BlockLength", - (u32) acpi_gbl_FADT. - gpe1_block_length); - } - - return (AE_OK); -} - /****************************************************************************** * * FUNCTION: acpi_ut_terminate diff --git a/drivers/acpi/utilities/utxface.c b/drivers/acpi/utilities/utxface.c index 7ea2981..bec0f54 100644 --- a/drivers/acpi/utilities/utxface.c +++ b/drivers/acpi/utilities/utxface.c @@ -127,20 +127,6 @@ acpi_status acpi_enable_subsystem(u32 flags) ACPI_FUNCTION_TRACE(acpi_enable_subsystem); - /* - * We must initialize the hardware before we can enable ACPI. - * The values from the FADT are validated here. - */ - if (!(flags & ACPI_NO_HARDWARE_INIT)) { - ACPI_DEBUG_PRINT((ACPI_DB_EXEC, - "[Init] Initializing ACPI hardware\n")); - - status = acpi_hw_initialize(); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - } - /* Enable ACPI mode */ if (!(flags & ACPI_NO_ACPI_ENABLE)) { diff --git a/include/acpi/achware.h b/include/acpi/achware.h index 29b60a8..f3e9a03 100644 --- a/include/acpi/achware.h +++ b/include/acpi/achware.h @@ -61,8 +61,6 @@ /* * hwacpi - high level functions */ -acpi_status acpi_hw_initialize(void); - acpi_status acpi_hw_set_mode(u32 mode); u32 acpi_hw_get_mode(void); diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 9183de1..6294734 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -45,6 +45,11 @@ #define __ACTABLES_H__ /* + * tbfadt - FADT parse/convert/validate + */ +void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags); + +/* * tbfind - find ACPI table */ acpi_status @@ -97,6 +102,10 @@ u8 acpi_tb_checksum(u8 * buffer, acpi_native_uint length); acpi_status acpi_tb_verify_checksum(struct acpi_table_header *table, u32 length); +void +acpi_tb_install_table(acpi_physical_address address, + u8 flags, char *signature, acpi_native_uint table_index); + acpi_status acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags); diff --git a/include/acpi/acutils.h b/include/acpi/acutils.h index 3c66f54..ba7d7e9 100644 --- a/include/acpi/acutils.h +++ b/include/acpi/acutils.h @@ -141,8 +141,6 @@ acpi_status acpi_ut_hardware_initialize(void); void acpi_ut_subsystem_shutdown(void); -acpi_status acpi_ut_validate_fadt(void); - /* * utclib - Local implementations of C library functions */ -- cgit v0.10.2 From e56b638bbee3c17b0dee39495bd15afe64db1b94 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Update comments in tbfadt.c Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c index 2336a72..62485d3 100644 --- a/drivers/acpi/tables/tbfadt.c +++ b/drivers/acpi/tables/tbfadt.c @@ -195,8 +195,8 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) * * DESCRIPTION: Converts all versions of the FADT to a common internal format. * - * NOTE: acpi_gbl_FADT must be of size (struct acpi_table_fadt), and must contain - * a copy of the actual FADT. + * NOTE: acpi_gbl_FADT must be of size (struct acpi_table_fadt), + * and must contain a copy of the actual FADT. * * ACPICA will use the "X" fields of the FADT for all addresses. * @@ -292,9 +292,10 @@ static void acpi_tb_convert_fadt(void) * * PARAMETERS: None * - * RETURN: Status + * RETURN: None * - * DESCRIPTION: Validate various ACPI registers in the FADT + * DESCRIPTION: Validate various ACPI registers in the FADT. For problems, + * issue a message, but no status is returned. * ******************************************************************************/ @@ -375,6 +376,6 @@ static void acpi_tb_validate_fadt(void) static void acpi_tb_fadt_register_error(char *register_name, u32 value) { - ACPI_WARNING((AE_INFO, "Invalid FADT value \"%s\" = %X", + ACPI_WARNING((AE_INFO, "Invalid FADT value in field \"%s\" = %X", register_name, value)); } -- cgit v0.10.2 From 694b0b2092bce3f4610626b04158a6f3a95058e6 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: add ASF comment Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/actbl1.h b/include/acpi/actbl1.h index 515d82c..8494c42 100644 --- a/include/acpi/actbl1.h +++ b/include/acpi/actbl1.h @@ -97,6 +97,8 @@ struct acpi_subtable_header { * * ASF - Alert Standard Format table (Signature "ASF!") * + * Conforms to the Alert Standard Format Specification V2.0, 23 April 2003 + * ******************************************************************************/ struct acpi_table_asf { -- cgit v0.10.2 From 77389e1263a7c9bc8040bda726e08b6501ba1c8b Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: re-factor table init routines for benefit of iASL Required new table init interface since iASL does not use RSDP/XSDT. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 94544a6..9d451e8 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -54,6 +54,29 @@ static acpi_status acpi_tb_load_namespace(void); /******************************************************************************* * + * FUNCTION: acpi_allocate_root_table + * + * PARAMETERS: initial_table_count - Size of initial_table_array, in number of + * struct acpi_table_desc structures + * + * RETURN: Status + * + * DESCRIPTION: Allocate a root table array. Used by i_aSL compiler and + * acpi_initialize_tables. + * + ******************************************************************************/ + +acpi_status acpi_allocate_root_table(u32 initial_table_count) +{ + + acpi_gbl_root_table_list.size = initial_table_count; + acpi_gbl_root_table_list.flags = ACPI_ROOT_ALLOW_RESIZE; + + return (acpi_tb_resize_root_table_list()); +} + +/******************************************************************************* + * * FUNCTION: acpi_initialize_tables * * PARAMETERS: initial_table_array - Pointer to an array of pre-allocated @@ -79,7 +102,7 @@ static acpi_status acpi_tb_load_namespace(void); ******************************************************************************/ acpi_status __init -acpi_initialize_tables(struct acpi_table_desc *initial_table_array, +acpi_initialize_tables(struct acpi_table_desc * initial_table_array, u32 initial_table_count, u8 allow_resize) { acpi_physical_address rsdp_address; @@ -92,10 +115,7 @@ acpi_initialize_tables(struct acpi_table_desc *initial_table_array, * Allocate the table array if requested */ if (!initial_table_array) { - acpi_gbl_root_table_list.size = initial_table_count; - acpi_gbl_root_table_list.flags = ACPI_ROOT_ALLOW_RESIZE; - - status = acpi_tb_resize_root_table_list(); + status = acpi_allocate_root_table(initial_table_count); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 6294734..99fa51a 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -44,6 +44,8 @@ #ifndef __ACTABLES_H__ #define __ACTABLES_H__ +acpi_status acpi_allocate_root_table(u32 initial_table_count); + /* * tbfadt - FADT parse/convert/validate */ -- cgit v0.10.2 From 15f0c0d1ef7804d098fe3eb0a3f350a490ca269c Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Allow type ANY to be the target of the Scope operator. Useful during disassembly where the target may be in a different table and thus the type is unknown. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dswload.c b/drivers/acpi/dispatcher/dswload.c index e3ca7f6..d60d062 100644 --- a/drivers/acpi/dispatcher/dswload.c +++ b/drivers/acpi/dispatcher/dswload.c @@ -196,6 +196,7 @@ acpi_ds_load1_begin_op(struct acpi_walk_state * walk_state, * one of the opcodes that actually opens a scope */ switch (node->type) { + case ACPI_TYPE_ANY: case ACPI_TYPE_LOCAL_SCOPE: /* Scope */ case ACPI_TYPE_DEVICE: case ACPI_TYPE_POWER: @@ -669,6 +670,7 @@ acpi_ds_load2_begin_op(struct acpi_walk_state *walk_state, * one of the opcodes that actually opens a scope */ switch (node->type) { + case ACPI_TYPE_ANY: case ACPI_TYPE_LOCAL_SCOPE: /* Scope */ case ACPI_TYPE_DEVICE: case ACPI_TYPE_POWER: -- cgit v0.10.2 From cc2a472b8411ce0b71738039e15d45917da30fbe Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: IsResourceTemplate now returns ACPI_STATUS to differentiate the failure modes. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acdisasm.h b/include/acpi/acdisasm.h index 722583a..b29d77a 100644 --- a/include/acpi/acdisasm.h +++ b/include/acpi/acdisasm.h @@ -140,7 +140,9 @@ extern const char *acpi_gbl_match_ops[]; extern struct acpi_dmtable_info acpi_dm_table_info_asf0[]; extern struct acpi_dmtable_info acpi_dm_table_info_asf1[]; +extern struct acpi_dmtable_info acpi_dm_table_info_asf1a[]; extern struct acpi_dmtable_info acpi_dm_table_info_asf2[]; +extern struct acpi_dmtable_info acpi_dm_table_info_asf2a[]; extern struct acpi_dmtable_info acpi_dm_table_info_asf3[]; extern struct acpi_dmtable_info acpi_dm_table_info_asf4[]; extern struct acpi_dmtable_info acpi_dm_table_info_asf_hdr[]; @@ -322,7 +324,7 @@ acpi_dm_resource_template(struct acpi_op_walk_info *info, union acpi_parse_object *op, u8 * byte_data, u32 byte_count); -u8 acpi_dm_is_resource_template(union acpi_parse_object *op); +acpi_status acpi_dm_is_resource_template(union acpi_parse_object *op); void acpi_dm_indent(u32 level); -- cgit v0.10.2 From 775d85b6aa33116da8aacad4168c540ce86a1803 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Add declarations for ASF! sub-tables Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/actbl1.h b/include/acpi/actbl1.h index 8494c42..3156d1a 100644 --- a/include/acpi/actbl1.h +++ b/include/acpi/actbl1.h @@ -148,7 +148,21 @@ struct acpi_asf_alert { u8 deassert_mask; u8 alerts; u8 data_length; - u8 array[1]; +}; + +struct acpi_asf_alert_data { + u8 address; + u8 command; + u8 mask; + u8 value; + u8 sensor_type; + u8 type; + u8 offset; + u8 source_type; + u8 severity; + u8 sensor_number; + u8 entity; + u8 instance; }; /* 2: ASF Remote Control */ @@ -158,7 +172,13 @@ struct acpi_asf_remote { u8 controls; u8 data_length; u16 reserved2; - u8 array[1]; +}; + +struct acpi_asf_control_data { + u8 function; + u8 address; + u8 command; + u8 value; }; /* 3: ASF RMCP Boot Options */ @@ -180,7 +200,6 @@ struct acpi_asf_address { struct acpi_asf_header header; u8 eprom_address; u8 devices; - u8 smbus_addresses[1]; }; /******************************************************************************* -- cgit v0.10.2 From ea5d8ebcbb7ca3bcb35a2133805571295f3f06e8 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: FADT verification is now table driven. Disassembler now verifies an input Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c index 62485d3..8816bab 100644 --- a/drivers/acpi/tables/tbfadt.c +++ b/drivers/acpi/tables/tbfadt.c @@ -49,74 +49,92 @@ ACPI_MODULE_NAME("tbfadt") /* Local prototypes */ static void inline -acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, +acpi_tb_init_generic_address(struct acpi_generic_address *generic_address, u8 bit_width, u64 address); -static void acpi_tb_fadt_register_error(char *register_name, u32 value); +/* Table for conversion of FADT to common internal format and FADT validation */ -static void acpi_tb_convert_fadt(void); - -static void acpi_tb_validate_fadt(void); - -/* Table used for conversion of FADT to common format */ - -typedef struct acpi_fadt_conversion { +typedef struct acpi_fadt_info { + char *name; u8 target; u8 source; u8 length; + u8 type; -} acpi_fadt_conversion; +} acpi_fadt_info; -static struct acpi_fadt_conversion fadt_conversion_table[] = { - {ACPI_FADT_OFFSET(xpm1a_event_block), +#define ACPI_FADT_REQUIRED 1 +#define ACPI_FADT_SEPARATE_LENGTH 2 + +static struct acpi_fadt_info fadt_info_table[] = { + {"Pm1aEventBlock", ACPI_FADT_OFFSET(xpm1a_event_block), ACPI_FADT_OFFSET(pm1a_event_block), - ACPI_FADT_OFFSET(pm1_event_length)}, - {ACPI_FADT_OFFSET(xpm1b_event_block), + ACPI_FADT_OFFSET(pm1_event_length), ACPI_FADT_REQUIRED}, + + {"Pm1bEventBlock", ACPI_FADT_OFFSET(xpm1b_event_block), ACPI_FADT_OFFSET(pm1b_event_block), - ACPI_FADT_OFFSET(pm1_event_length)}, - {ACPI_FADT_OFFSET(xpm1a_control_block), + ACPI_FADT_OFFSET(pm1_event_length), 0}, + + {"Pm1aControlBlock", ACPI_FADT_OFFSET(xpm1a_control_block), ACPI_FADT_OFFSET(pm1a_control_block), - ACPI_FADT_OFFSET(pm1_control_length)}, - {ACPI_FADT_OFFSET(xpm1b_control_block), + ACPI_FADT_OFFSET(pm1_control_length), ACPI_FADT_REQUIRED}, + + {"Pm1bControlBlock", ACPI_FADT_OFFSET(xpm1b_control_block), ACPI_FADT_OFFSET(pm1b_control_block), - ACPI_FADT_OFFSET(pm1_control_length)}, - {ACPI_FADT_OFFSET(xpm2_control_block), + ACPI_FADT_OFFSET(pm1_control_length), 0}, + + {"Pm2ControlBlock", ACPI_FADT_OFFSET(xpm2_control_block), ACPI_FADT_OFFSET(pm2_control_block), - ACPI_FADT_OFFSET(pm2_control_length)}, - {ACPI_FADT_OFFSET(xpm_timer_block), ACPI_FADT_OFFSET(pm_timer_block), - ACPI_FADT_OFFSET(pm_timer_length)}, - {ACPI_FADT_OFFSET(xgpe0_block), ACPI_FADT_OFFSET(gpe0_block), - ACPI_FADT_OFFSET(gpe0_block_length)}, - {ACPI_FADT_OFFSET(xgpe1_block), ACPI_FADT_OFFSET(gpe1_block), - ACPI_FADT_OFFSET(gpe1_block_length)} + ACPI_FADT_OFFSET(pm2_control_length), ACPI_FADT_SEPARATE_LENGTH}, + + {"PmTimerBlock", ACPI_FADT_OFFSET(xpm_timer_block), + ACPI_FADT_OFFSET(pm_timer_block), + ACPI_FADT_OFFSET(pm_timer_length), ACPI_FADT_REQUIRED}, + + {"Gpe0Block", ACPI_FADT_OFFSET(xgpe0_block), + ACPI_FADT_OFFSET(gpe0_block), + ACPI_FADT_OFFSET(gpe0_block_length), ACPI_FADT_SEPARATE_LENGTH}, + + {"Gpe1Block", ACPI_FADT_OFFSET(xgpe1_block), + ACPI_FADT_OFFSET(gpe1_block), + ACPI_FADT_OFFSET(gpe1_block_length), ACPI_FADT_SEPARATE_LENGTH} }; -#define ACPI_FADT_CONVERSION_ENTRIES (sizeof (fadt_conversion_table) / sizeof (struct acpi_fadt_conversion)) +#define ACPI_FADT_INFO_ENTRIES (sizeof (fadt_info_table) / sizeof (struct acpi_fadt_info)) /******************************************************************************* * * FUNCTION: acpi_tb_init_generic_address * - * PARAMETERS: new_gas_struct - GAS struct to be initialized + * PARAMETERS: generic_address - GAS struct to be initialized * bit_width - Width of this register * Address - Address of the register * * RETURN: None * - * DESCRIPTION: Initialize a GAS structure. + * DESCRIPTION: Initialize a Generic Address Structure (GAS) + * See the ACPI specification for a full description and + * definition of this structure. * ******************************************************************************/ static void inline -acpi_tb_init_generic_address(struct acpi_generic_address *new_gas_struct, +acpi_tb_init_generic_address(struct acpi_generic_address *generic_address, u8 bit_width, u64 address) { - ACPI_MOVE_64_TO_64(&new_gas_struct->address, &address); - new_gas_struct->space_id = ACPI_ADR_SPACE_SYSTEM_IO; - new_gas_struct->bit_width = bit_width; - new_gas_struct->bit_offset = 0; - new_gas_struct->access_width = 0; + /* + * The 64-bit Address field is non-aligned in the byte packed + * GAS struct. + */ + ACPI_MOVE_64_TO_64(&generic_address->address, &address); + + /* All other fields are byte-wide */ + + generic_address->space_id = ACPI_ADR_SPACE_SYSTEM_IO; + generic_address->bit_width = bit_width; + generic_address->bit_offset = 0; + generic_address->access_width = 0; } /******************************************************************************* @@ -139,8 +157,8 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) struct acpi_table_header *table; /* - * Special case for the FADT because of multiple versions and the fact - * that it contains pointers to both the DSDT and FACS tables. + * The FADT has multiple versions with different lengths, + * and it contains pointers to both the DSDT and FACS tables. * * Get a local copy of the FADT and convert it to a common format * Map entire FADT, assumed to be smaller than one page. @@ -160,29 +178,41 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) */ (void)acpi_tb_verify_checksum(table, length); - /* Copy the entire FADT locally */ + /* + * If the FADT is larger than what we know about, we have a problem. + * Truncate the table, but make some noise. + */ + if (length > sizeof(struct acpi_table_fadt)) { + ACPI_WARNING((AE_INFO, + "FADT (revision %u) is too large, truncating length 0x%X to 0x%X", + table->revision, length, + sizeof(struct acpi_table_fadt))); + } - ACPI_MEMSET(&acpi_gbl_FADT, 0, sizeof(struct acpi_table_fadt)); + /* Copy the entire FADT locally. Zero first for tb_convert_fadt */ + ACPI_MEMSET(&acpi_gbl_FADT, 0, sizeof(struct acpi_table_fadt)); ACPI_MEMCPY(&acpi_gbl_FADT, table, ACPI_MIN(length, sizeof(struct acpi_table_fadt))); - acpi_os_unmap_memory(table, length); - /* Convert local FADT to the common internal format */ + /* All done with the real FADT, unmap it */ + + acpi_os_unmap_memory(table, length); + /* + * 1) Convert the local copy of the FADT to the common internal format + * 2) Validate some of the important values within the FADT + */ acpi_tb_convert_fadt(); + acpi_tb_validate_fadt(&acpi_gbl_FADT); - /* Extract the DSDT and FACS tables from the FADT */ + /* Obtain the DSDT and FACS tables via their addresses within the FADT */ acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt, flags, ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT); acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xfacs, flags, ACPI_SIG_FACS, ACPI_TABLE_INDEX_FACS); - - /* Validate important FADT values */ - - acpi_tb_validate_fadt(); } /******************************************************************************* @@ -194,6 +224,7 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) * RETURN: None * * DESCRIPTION: Converts all versions of the FADT to a common internal format. + * -> Expand all 32-bit addresses to 64-bit. * * NOTE: acpi_gbl_FADT must be of size (struct acpi_table_fadt), * and must contain a copy of the actual FADT. @@ -213,13 +244,17 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) * ******************************************************************************/ -static void acpi_tb_convert_fadt(void) +void acpi_tb_convert_fadt(void) { u8 pm1_register_length; struct acpi_generic_address *target; acpi_native_uint i; - /* Expand the FACS and DSDT addresses as necessary */ + /* Update the local FADT table header length */ + + acpi_gbl_FADT.header.length = sizeof(struct acpi_table_fadt); + + /* Expand the 32-bit FACS and DSDT addresses to 64-bit as necessary */ if (!acpi_gbl_FADT.Xfacs) { acpi_gbl_FADT.Xfacs = (u64) acpi_gbl_FADT.facs; @@ -233,10 +268,10 @@ static void acpi_tb_convert_fadt(void) * Expand the 32-bit V1.0 addresses to the 64-bit "X" generic address * structures as necessary. */ - for (i = 0; i < ACPI_FADT_CONVERSION_ENTRIES; i++) { + for (i = 0; i < ACPI_FADT_INFO_ENTRIES; i++) { target = ACPI_ADD_PTR(struct acpi_generic_address, &acpi_gbl_FADT, - fadt_conversion_table[i].target); + fadt_info_table[i].target); /* Expand only if the X target is null */ @@ -244,11 +279,11 @@ static void acpi_tb_convert_fadt(void) acpi_tb_init_generic_address(target, *ACPI_ADD_PTR(u8, &acpi_gbl_FADT, - fadt_conversion_table + fadt_info_table [i].length), (u64) * ACPI_ADD_PTR(u32, &acpi_gbl_FADT, - fadt_conversion_table + fadt_info_table [i]. source)); } @@ -265,14 +300,14 @@ static void acpi_tb_convert_fadt(void) */ pm1_register_length = (u8) ACPI_DIV_2(acpi_gbl_FADT.pm1_event_length); - /* PM1A is required */ + /* The PM1A register block is required */ acpi_tb_init_generic_address(&acpi_gbl_xpm1a_enable, pm1_register_length, (acpi_gbl_FADT.xpm1a_event_block.address + pm1_register_length)); - /* PM1B is optional; leave null if not present */ + /* The PM1B register block is optional, ignore if not present */ if (acpi_gbl_FADT.xpm1b_event_block.address) { acpi_tb_init_generic_address(&acpi_gbl_xpm1b_enable, @@ -280,102 +315,84 @@ static void acpi_tb_convert_fadt(void) (acpi_gbl_FADT.xpm1b_event_block. address + pm1_register_length)); } - - /* Global FADT is the new common V2.0 FADT */ - - acpi_gbl_FADT.header.length = sizeof(struct acpi_table_fadt); } /****************************************************************************** * * FUNCTION: acpi_tb_validate_fadt * - * PARAMETERS: None + * PARAMETERS: Table - Pointer to the FADT to be validated * * RETURN: None * - * DESCRIPTION: Validate various ACPI registers in the FADT. For problems, - * issue a message, but no status is returned. + * DESCRIPTION: Validate various important fields within the FADT. If a problem + * is found, issue a message, but no status is returned. + * Used by both the table manager and the disassembler. + * + * Possible additional checks: + * (acpi_gbl_FADT.pm1_event_length >= 4) + * (acpi_gbl_FADT.pm1_control_length >= 2) + * (acpi_gbl_FADT.pm_timer_length >= 4) + * Gpe block lengths must be multiple of 2 * ******************************************************************************/ -static void acpi_tb_validate_fadt(void) +void acpi_tb_validate_fadt(struct acpi_table_fadt *table) { + u32 *address32; + struct acpi_generic_address *address64; + u8 length; + acpi_native_uint i; - /* These length fields have a minimum value */ - - if (acpi_gbl_FADT.pm1_event_length < 4) { - acpi_tb_fadt_register_error("Pm1EventLength", - (u32) acpi_gbl_FADT. - pm1_event_length); - } - - if (acpi_gbl_FADT.pm_timer_length < 4) { - acpi_tb_fadt_register_error("PmTimerLength", - (u32) acpi_gbl_FADT. - pm_timer_length); - } - - /* These length and address fields must be non-zero */ - - if (!acpi_gbl_FADT.pm1_control_length) { - acpi_tb_fadt_register_error("Pm1ControlLength", 0); - } - - if (!acpi_gbl_FADT.xpm1a_event_block.address) { - acpi_tb_fadt_register_error("XPm1aEventBlock.Address", 0); - } - - if (!acpi_gbl_FADT.xpm1a_control_block.address) { - acpi_tb_fadt_register_error("XPm1aControlBlock.Address", 0); - } - - if (!acpi_gbl_FADT.xpm_timer_block.address) { - acpi_tb_fadt_register_error("XPmTimerBlock.Address", 0); - } - - /* If PM2 block is present, must have non-zero length */ - - if ((acpi_gbl_FADT.xpm2_control_block.address && - !acpi_gbl_FADT.pm2_control_length)) { - acpi_tb_fadt_register_error("Pm2ControlLength", - (u32) acpi_gbl_FADT. - pm2_control_length); - } - - /* Length of any valid GPE blocks must be a multiple of 2 */ + /* Examine all of the 64-bit extended address fields (X fields) */ + + for (i = 0; i < ACPI_FADT_INFO_ENTRIES; i++) { + + /* Generate pointers to the 32-bit and 64-bit addresses and get the length */ + + address64 = + ACPI_ADD_PTR(struct acpi_generic_address, table, + fadt_info_table[i].target); + address32 = ACPI_ADD_PTR(u32, table, fadt_info_table[i].source); + length = *ACPI_ADD_PTR(u8, table, fadt_info_table[i].length); + + if (fadt_info_table[i].type & ACPI_FADT_REQUIRED) { + /* + * Field is required (Pm1a_event, Pm1a_control, pm_timer). + * Both the address and length must be non-zero. + */ + if (!address64->address || !length) { + ACPI_ERROR((AE_INFO, + "Required field \"%s\" has zero address and/or length: %8.8X%8.8X/%X", + fadt_info_table[i].name, + ACPI_FORMAT_UINT64(address64-> + address), + length)); + } + } else if (fadt_info_table[i].type & ACPI_FADT_SEPARATE_LENGTH) { + /* + * Field is optional (PM2Control, GPE0, GPE1) AND has its own + * length field. If present, both the address and length must be valid. + */ + if ((address64->address && !length) + || (!address64->address && length)) { + ACPI_WARNING((AE_INFO, + "Optional field \"%s\" has zero address or length: %8.8X%8.8X/%X", + fadt_info_table[i].name, + ACPI_FORMAT_UINT64(address64-> + address), + length)); + } + } - if (acpi_gbl_FADT.xgpe0_block.address && - (acpi_gbl_FADT.gpe0_block_length & 1)) { - acpi_tb_fadt_register_error("Gpe0BlockLength", - (u32) acpi_gbl_FADT. - gpe0_block_length); - } + /* If both 32- and 64-bit addresses are valid (non-zero), they must match */ - if (acpi_gbl_FADT.xgpe1_block.address && - (acpi_gbl_FADT.gpe1_block_length & 1)) { - acpi_tb_fadt_register_error("Gpe1BlockLength", - (u32) acpi_gbl_FADT. - gpe1_block_length); + if (address64->address && *address32 && + (address64->address != (u64) * address32)) { + ACPI_ERROR((AE_INFO, + "32/64X address mismatch in \"%s\": [%8.8X] [%8.8X%8.8X], using 64X", + fadt_info_table[i].name, *address32, + ACPI_FORMAT_UINT64(address64->address))); + } } } - -/******************************************************************************* - * - * FUNCTION: acpi_tb_fadt_register_error - * - * PARAMETERS: register_name - Pointer to string identifying register - * Value - Actual register contents value - * - * RETURN: None - * - * DESCRIPTION: Display FADT warning message - * - ******************************************************************************/ - -static void acpi_tb_fadt_register_error(char *register_name, u32 value) -{ - - ACPI_WARNING((AE_INFO, "Invalid FADT value in field \"%s\" = %X", - register_name, value)); -} diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 54e53e6..1033748 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -280,7 +280,7 @@ acpi_tb_get_root_table_entry(u8 * table_entry, #if ACPI_MACHINE_WIDTH == 32 if (address64 > ACPI_UINT32_MAX) { - /* Will truncate 64-bit address to 32 bits */ + /* Will truncate 64-bit address to 32 bits, issue warning */ ACPI_WARNING((AE_INFO, "64-bit Physical Address in XSDT is too large (%8.8X%8.8X), truncating", diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 99fa51a..65a69ca 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -51,6 +51,10 @@ acpi_status acpi_allocate_root_table(u32 initial_table_count); */ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags); +void acpi_tb_convert_fadt(void); + +void acpi_tb_validate_fadt(struct acpi_table_fadt *table); + /* * tbfind - find ACPI table */ -- cgit v0.10.2 From 13b572a35ed904ae1e162f8ee89ca7fd6992b44c Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Report error if method creates 2 objects with the same name Fixed a regression where an error was no longer emitted if a control method attempts to create 2 objects of the same name. This previously and now returns AE_ALREADY_EXISTS. When this exception occurs, it invokes the mechanism that will dynamically serialize the control method to possible prevent future errors. (BZ 440) Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dswload.c b/drivers/acpi/dispatcher/dswload.c index d60d062..565d455 100644 --- a/drivers/acpi/dispatcher/dswload.c +++ b/drivers/acpi/dispatcher/dswload.c @@ -547,6 +547,7 @@ acpi_ds_load2_begin_op(struct acpi_walk_state *walk_state, acpi_status status; acpi_object_type object_type; char *buffer_ptr; + u32 flags; ACPI_FUNCTION_TRACE(ds_load2_begin_op); @@ -752,12 +753,20 @@ acpi_ds_load2_begin_op(struct acpi_walk_state *walk_state, break; } - /* Add new entry into namespace */ + flags = ACPI_NS_NO_UPSEARCH; + if (walk_state->pass_number == 3) { + + /* Execution mode, node cannot already exist */ + + flags |= ACPI_NS_ERROR_IF_FOUND; + } + + /* Add new entry or lookup existing entry */ status = acpi_ns_lookup(walk_state->scope_info, buffer_ptr, - object_type, ACPI_IMODE_LOAD_PASS2, - ACPI_NS_NO_UPSEARCH, walk_state, &(node)); + object_type, ACPI_IMODE_LOAD_PASS2, flags, + walk_state, &node); break; } diff --git a/drivers/acpi/parser/psparse.c b/drivers/acpi/parser/psparse.c index a02aa62..6e875ce 100644 --- a/drivers/acpi/parser/psparse.c +++ b/drivers/acpi/parser/psparse.c @@ -540,6 +540,11 @@ acpi_status acpi_ps_parse_aml(struct acpi_walk_state *walk_state) if ((status == AE_ALREADY_EXISTS) && (!walk_state->method_desc->method.mutex)) { + ACPI_INFO((AE_INFO, + "Marking method %4.4s as Serialized", + walk_state->method_node->name. + ascii)); + /* * Method tried to create an object twice. The probable cause is * that the method cannot handle reentrancy. -- cgit v0.10.2 From 7139284460fba90c4dfcfae76680ad36b45f5982 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: New common routine for creating and verifying a local FADT. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c index 8816bab..31a4a00 100644 --- a/drivers/acpi/tables/tbfadt.c +++ b/drivers/acpi/tables/tbfadt.c @@ -52,6 +52,10 @@ static void inline acpi_tb_init_generic_address(struct acpi_generic_address *generic_address, u8 bit_width, u64 address); +static void acpi_tb_convert_fadt(void); + +static void acpi_tb_validate_fadt(void); + /* Table for conversion of FADT to common internal format and FADT validation */ typedef struct acpi_fadt_info { @@ -178,13 +182,47 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) */ (void)acpi_tb_verify_checksum(table, length); + /* Obtain a local copy of the FADT in common ACPI 2.0+ format */ + + acpi_tb_create_local_fadt(table, length); + + /* All done with the real FADT, unmap it */ + + acpi_os_unmap_memory(table, length); + + /* Obtain the DSDT and FACS tables via their addresses within the FADT */ + + acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt, + flags, ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT); + + acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xfacs, + flags, ACPI_SIG_FACS, ACPI_TABLE_INDEX_FACS); +} + +/******************************************************************************* + * + * FUNCTION: acpi_tb_create_local_fadt + * + * PARAMETERS: Table - Pointer to BIOS FADT + * Length - Length of the table + * + * RETURN: None + * + * DESCRIPTION: Get a local copy of the FADT and convert it to a common format. + * Performs validation on some important FADT fields. + * + ******************************************************************************/ + +void acpi_tb_create_local_fadt(struct acpi_table_header *table, u32 length) +{ + /* - * If the FADT is larger than what we know about, we have a problem. + * Check if the FADT is larger than what we know about (ACPI 2.0 version). * Truncate the table, but make some noise. */ if (length > sizeof(struct acpi_table_fadt)) { ACPI_WARNING((AE_INFO, - "FADT (revision %u) is too large, truncating length 0x%X to 0x%X", + "FADT (revision %u) is longer than ACPI 2.0 version, truncating length 0x%X to 0x%X", table->revision, length, sizeof(struct acpi_table_fadt))); } @@ -192,27 +230,16 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) /* Copy the entire FADT locally. Zero first for tb_convert_fadt */ ACPI_MEMSET(&acpi_gbl_FADT, 0, sizeof(struct acpi_table_fadt)); + ACPI_MEMCPY(&acpi_gbl_FADT, table, ACPI_MIN(length, sizeof(struct acpi_table_fadt))); - /* All done with the real FADT, unmap it */ - - acpi_os_unmap_memory(table, length); - /* * 1) Convert the local copy of the FADT to the common internal format * 2) Validate some of the important values within the FADT */ acpi_tb_convert_fadt(); - acpi_tb_validate_fadt(&acpi_gbl_FADT); - - /* Obtain the DSDT and FACS tables via their addresses within the FADT */ - - acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xdsdt, - flags, ACPI_SIG_DSDT, ACPI_TABLE_INDEX_DSDT); - - acpi_tb_install_table((acpi_physical_address) acpi_gbl_FADT.Xfacs, - flags, ACPI_SIG_FACS, ACPI_TABLE_INDEX_FACS); + acpi_tb_validate_fadt(); } /******************************************************************************* @@ -244,7 +271,7 @@ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags) * ******************************************************************************/ -void acpi_tb_convert_fadt(void) +static void acpi_tb_convert_fadt(void) { u8 pm1_register_length; struct acpi_generic_address *target; @@ -337,7 +364,7 @@ void acpi_tb_convert_fadt(void) * ******************************************************************************/ -void acpi_tb_validate_fadt(struct acpi_table_fadt *table) +static void acpi_tb_validate_fadt(void) { u32 *address32; struct acpi_generic_address *address64; @@ -351,10 +378,14 @@ void acpi_tb_validate_fadt(struct acpi_table_fadt *table) /* Generate pointers to the 32-bit and 64-bit addresses and get the length */ address64 = - ACPI_ADD_PTR(struct acpi_generic_address, table, + ACPI_ADD_PTR(struct acpi_generic_address, &acpi_gbl_FADT, fadt_info_table[i].target); - address32 = ACPI_ADD_PTR(u32, table, fadt_info_table[i].source); - length = *ACPI_ADD_PTR(u8, table, fadt_info_table[i].length); + address32 = + ACPI_ADD_PTR(u32, &acpi_gbl_FADT, + fadt_info_table[i].source); + length = + *ACPI_ADD_PTR(u8, &acpi_gbl_FADT, + fadt_info_table[i].length); if (fadt_info_table[i].type & ACPI_FADT_REQUIRED) { /* diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 65a69ca..4079f8a 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -51,9 +51,7 @@ acpi_status acpi_allocate_root_table(u32 initial_table_count); */ void acpi_tb_parse_fadt(acpi_native_uint table_index, u8 flags); -void acpi_tb_convert_fadt(void); - -void acpi_tb_validate_fadt(struct acpi_table_fadt *table); +void acpi_tb_create_local_fadt(struct acpi_table_header *table, u32 length); /* * tbfind - find ACPI table -- cgit v0.10.2 From 0fab8997f18f71b2391e72e49d8d31a395352dcc Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Fix memory leak in table load error path Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/executer/exconfig.c b/drivers/acpi/executer/exconfig.c index dd43b00..20a5ab8 100644 --- a/drivers/acpi/executer/exconfig.c +++ b/drivers/acpi/executer/exconfig.c @@ -413,7 +413,7 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, */ status = acpi_tb_add_table(table_ptr, &table_index); if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + goto cleanup; } status = -- cgit v0.10.2 From 977a6226feae3e2c10a4d8227625ff0f04b49239 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Fix trace output name and whitespace Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/executer/exutils.c b/drivers/acpi/executer/exutils.c index 72adcf4..e32d489 100644 --- a/drivers/acpi/executer/exutils.c +++ b/drivers/acpi/executer/exutils.c @@ -88,7 +88,7 @@ void acpi_ex_enter_interpreter(void) { acpi_status status; - ACPI_FUNCTION_TRACE(ex_reacquire_interpreter); + ACPI_FUNCTION_TRACE(ex_enter_interpreter); status = acpi_ut_acquire_mutex(ACPI_MTX_INTERPRETER); if (ACPI_FAILURE(status)) { @@ -116,7 +116,6 @@ void acpi_ex_enter_interpreter(void) void acpi_ex_reacquire_interpreter(void) { - ACPI_FUNCTION_TRACE(ex_reacquire_interpreter); /* @@ -185,7 +184,6 @@ void acpi_ex_exit_interpreter(void) void acpi_ex_relinquish_interpreter(void) { - ACPI_FUNCTION_TRACE(ex_relinquish_interpreter); /* -- cgit v0.10.2 From 4cdf469090f732ab8a45b2d30b43ec5745699285 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:20 +0300 Subject: ACPICA: Update version to 20060912 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index 4db7858..7b02a13 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20060831 +#define ACPI_CA_VERSION 0x20060912 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, -- cgit v0.10.2 From 14d64b5e36a82ef21a51d8a15639d26b75a79499 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Add full table name to disassembler output Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acdisasm.h b/include/acpi/acdisasm.h index b29d77a..ea35f1f 100644 --- a/include/acpi/acdisasm.h +++ b/include/acpi/acdisasm.h @@ -101,6 +101,7 @@ typedef const struct acpi_dmtable_info { #define ACPI_DMT_MADT 24 #define ACPI_DMT_SRAT 25 #define ACPI_DMT_EXIT 26 +#define ACPI_DMT_SIG 27 typedef void (*ACPI_TABLE_HANDLER) (struct acpi_table_header * table); @@ -109,6 +110,7 @@ struct acpi_dmtable_data { char *signature; struct acpi_dmtable_info *table_info; ACPI_TABLE_HANDLER table_handler; + char *name; }; struct acpi_op_walk_info { -- cgit v0.10.2 From 73ca0fbcc25a6080db4136f55dbcd5fe7b33398f Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Fix for Global Lock semaphore. Fixed a problem with the Global Lock where the lock could appear to be obtained before it is actually obtained, semaphore created with one unit. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/namespace/nsaccess.c b/drivers/acpi/namespace/nsaccess.c index b2ef673..2529ae9 100644 --- a/drivers/acpi/namespace/nsaccess.c +++ b/drivers/acpi/namespace/nsaccess.c @@ -214,7 +214,7 @@ acpi_status acpi_ns_root_initialize(void) /* Create additional counting semaphore for global lock */ status = - acpi_os_create_semaphore(1, 1, + acpi_os_create_semaphore(1, 0, &acpi_gbl_global_lock_semaphore); if (ACPI_FAILURE(status)) { acpi_ut_remove_reference -- cgit v0.10.2 From d8c71b6d3b21cf21ad775e1cf6da95bf87bd5ad4 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Remove obsolete Flags parameter. Remove flags parameter for acpi_{get,set}_register(). It is no longer necessary now that these functions use a spinlock for mutual exclusion. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evevent.c b/drivers/acpi/events/evevent.c index 6b4bc99..f09d1aa 100644 --- a/drivers/acpi/events/evevent.c +++ b/drivers/acpi/events/evevent.c @@ -204,8 +204,7 @@ static acpi_status acpi_ev_fixed_event_initialize(void) if (acpi_gbl_fixed_event_info[i].enable_register_id != 0xFF) { status = acpi_set_register(acpi_gbl_fixed_event_info[i]. - enable_register_id, 0, - ACPI_MTX_LOCK); + enable_register_id, 0); if (ACPI_FAILURE(status)) { return (status); } @@ -291,7 +290,7 @@ static u32 acpi_ev_fixed_event_dispatch(u32 event) /* Clear the status bit */ (void)acpi_set_register(acpi_gbl_fixed_event_info[event]. - status_register_id, 1, ACPI_MTX_DO_NOT_LOCK); + status_register_id, 1); /* * Make sure we've got a handler. If not, report an error. @@ -299,8 +298,7 @@ static u32 acpi_ev_fixed_event_dispatch(u32 event) */ if (NULL == acpi_gbl_fixed_event_handlers[event].handler) { (void)acpi_set_register(acpi_gbl_fixed_event_info[event]. - enable_register_id, 0, - ACPI_MTX_DO_NOT_LOCK); + enable_register_id, 0); ACPI_ERROR((AE_INFO, "No installed handler for fixed event [%08X]", diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index 21449f3..3bacede 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c @@ -493,7 +493,7 @@ acpi_status acpi_ev_release_global_lock(void) if (pending) { status = acpi_set_register(ACPI_BITREG_GLOBAL_LOCK_RELEASE, - 1, ACPI_MTX_LOCK); + 1); } ACPI_DEBUG_PRINT((ACPI_DB_EXEC, diff --git a/drivers/acpi/events/evxfevnt.c b/drivers/acpi/events/evxfevnt.c index 91e5f5b..a3d148e 100644 --- a/drivers/acpi/events/evxfevnt.c +++ b/drivers/acpi/events/evxfevnt.c @@ -157,7 +157,7 @@ acpi_status acpi_enable_event(u32 event, u32 flags) */ status = acpi_set_register(acpi_gbl_fixed_event_info[event]. - enable_register_id, 1, ACPI_MTX_LOCK); + enable_register_id, 1); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -166,7 +166,7 @@ acpi_status acpi_enable_event(u32 event, u32 flags) status = acpi_get_register(acpi_gbl_fixed_event_info[event]. - enable_register_id, &value, ACPI_MTX_LOCK); + enable_register_id, &value); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -356,14 +356,14 @@ acpi_status acpi_disable_event(u32 event, u32 flags) */ status = acpi_set_register(acpi_gbl_fixed_event_info[event]. - enable_register_id, 0, ACPI_MTX_LOCK); + enable_register_id, 0); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } status = acpi_get_register(acpi_gbl_fixed_event_info[event]. - enable_register_id, &value, ACPI_MTX_LOCK); + enable_register_id, &value); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -409,7 +409,7 @@ acpi_status acpi_clear_event(u32 event) */ status = acpi_set_register(acpi_gbl_fixed_event_info[event]. - status_register_id, 1, ACPI_MTX_LOCK); + status_register_id, 1); return_ACPI_STATUS(status); } @@ -498,7 +498,7 @@ acpi_status acpi_get_event_status(u32 event, acpi_event_status * event_status) status = acpi_get_register(acpi_gbl_fixed_event_info[event]. - status_register_id, event_status, ACPI_MTX_LOCK); + status_register_id, event_status); return_ACPI_STATUS(status); } diff --git a/drivers/acpi/hardware/hwacpi.c b/drivers/acpi/hardware/hwacpi.c index 9c7df71..dbcc4c0 100644 --- a/drivers/acpi/hardware/hwacpi.c +++ b/drivers/acpi/hardware/hwacpi.c @@ -171,8 +171,7 @@ u32 acpi_hw_get_mode(void) return_UINT32(ACPI_SYS_MODE_ACPI); } - status = - acpi_get_register(ACPI_BITREG_SCI_ENABLE, &value, ACPI_MTX_LOCK); + status = acpi_get_register(ACPI_BITREG_SCI_ENABLE, &value); if (ACPI_FAILURE(status)) { return_UINT32(ACPI_SYS_MODE_LEGACY); } diff --git a/drivers/acpi/hardware/hwregs.c b/drivers/acpi/hardware/hwregs.c index 9fe7adf..716e4ae 100644 --- a/drivers/acpi/hardware/hwregs.c +++ b/drivers/acpi/hardware/hwregs.c @@ -54,17 +54,15 @@ ACPI_MODULE_NAME("hwregs") * * FUNCTION: acpi_hw_clear_acpi_status * - * PARAMETERS: Flags - Lock the hardware or not + * PARAMETERS: None * - * RETURN: none + * RETURN: None * * DESCRIPTION: Clears all fixed and general purpose status bits * THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED * - * NOTE: TBD: Flags parameter is obsolete, to be removed - * ******************************************************************************/ -acpi_status acpi_hw_clear_acpi_status(u32 flags) +acpi_status acpi_hw_clear_acpi_status(void) { acpi_status status; acpi_cpu_flags lock_flags = 0; @@ -253,18 +251,15 @@ struct acpi_bit_register_info *acpi_hw_get_bit_register_info(u32 register_id) * * PARAMETERS: register_id - ID of ACPI bit_register to access * return_value - Value that was read from the register - * Flags - Lock the hardware or not * * RETURN: Status and the value read from specified Register. Value * returned is normalized to bit0 (is shifted all the way right) * * DESCRIPTION: ACPI bit_register read function. * - * NOTE: TBD: Flags parameter is obsolete, to be removed - * ******************************************************************************/ -acpi_status acpi_get_register(u32 register_id, u32 * return_value, u32 flags) +acpi_status acpi_get_register(u32 register_id, u32 * return_value) { u32 register_value = 0; struct acpi_bit_register_info *bit_reg_info; @@ -312,16 +307,13 @@ ACPI_EXPORT_SYMBOL(acpi_get_register) * PARAMETERS: register_id - ID of ACPI bit_register to access * Value - (only used on write) value to write to the * Register, NOT pre-normalized to the bit pos - * Flags - Lock the hardware or not * * RETURN: Status * * DESCRIPTION: ACPI Bit Register write function. * - * NOTE: TBD: Flags parameter is obsolete, to be removed - * ******************************************************************************/ -acpi_status acpi_set_register(u32 register_id, u32 value, u32 flags) +acpi_status acpi_set_register(u32 register_id, u32 value) { u32 register_value = 0; struct acpi_bit_register_info *bit_reg_info; diff --git a/drivers/acpi/hardware/hwsleep.c b/drivers/acpi/hardware/hwsleep.c index 6faa76b..7c96451 100644 --- a/drivers/acpi/hardware/hwsleep.c +++ b/drivers/acpi/hardware/hwsleep.c @@ -277,15 +277,14 @@ acpi_status asmlinkage acpi_enter_sleep_state(u8 sleep_state) /* Clear wake status */ - status = - acpi_set_register(ACPI_BITREG_WAKE_STATUS, 1, ACPI_MTX_DO_NOT_LOCK); + status = acpi_set_register(ACPI_BITREG_WAKE_STATUS, 1); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } /* Clear all fixed and general purpose status bits */ - status = acpi_hw_clear_acpi_status(ACPI_MTX_DO_NOT_LOCK); + status = acpi_hw_clear_acpi_status(); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -398,8 +397,7 @@ acpi_status asmlinkage acpi_enter_sleep_state(u8 sleep_state) /* Wait until we enter sleep state */ do { - status = acpi_get_register(ACPI_BITREG_WAKE_STATUS, &in_value, - ACPI_MTX_DO_NOT_LOCK); + status = acpi_get_register(ACPI_BITREG_WAKE_STATUS, &in_value); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -432,13 +430,12 @@ acpi_status asmlinkage acpi_enter_sleep_state_s4bios(void) ACPI_FUNCTION_TRACE(acpi_enter_sleep_state_s4bios); - status = - acpi_set_register(ACPI_BITREG_WAKE_STATUS, 1, ACPI_MTX_DO_NOT_LOCK); + status = acpi_set_register(ACPI_BITREG_WAKE_STATUS, 1); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } - status = acpi_hw_clear_acpi_status(ACPI_MTX_DO_NOT_LOCK); + status = acpi_hw_clear_acpi_status(); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -465,8 +462,7 @@ acpi_status asmlinkage acpi_enter_sleep_state_s4bios(void) do { acpi_os_stall(1000); - status = acpi_get_register(ACPI_BITREG_WAKE_STATUS, &in_value, - ACPI_MTX_DO_NOT_LOCK); + status = acpi_get_register(ACPI_BITREG_WAKE_STATUS, &in_value); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -599,13 +595,11 @@ acpi_status acpi_leave_sleep_state(u8 sleep_state) (void) acpi_set_register(acpi_gbl_fixed_event_info - [ACPI_EVENT_POWER_BUTTON].enable_register_id, 1, - ACPI_MTX_DO_NOT_LOCK); + [ACPI_EVENT_POWER_BUTTON].enable_register_id, 1); (void) acpi_set_register(acpi_gbl_fixed_event_info - [ACPI_EVENT_POWER_BUTTON].status_register_id, 1, - ACPI_MTX_DO_NOT_LOCK); + [ACPI_EVENT_POWER_BUTTON].status_register_id, 1); arg.integer.value = ACPI_SST_WORKING; status = acpi_evaluate_object(NULL, METHOD_NAME__SST, &arg_list, NULL); diff --git a/drivers/acpi/pci_link.c b/drivers/acpi/pci_link.c index 481e633..662e429 100644 --- a/drivers/acpi/pci_link.c +++ b/drivers/acpi/pci_link.c @@ -785,7 +785,7 @@ static int irqrouter_resume(struct sys_device *dev) /* Make sure SCI is enabled again (Apple firmware bug?) */ - acpi_set_register(ACPI_BITREG_SCI_ENABLE, 1, ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_SCI_ENABLE, 1); list_for_each(node, &acpi_link.entries) { link = list_entry(node, struct acpi_pci_link, node); diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c index 9fa3d39..db21dda 100644 --- a/drivers/acpi/processor_idle.c +++ b/drivers/acpi/processor_idle.c @@ -187,8 +187,7 @@ acpi_processor_power_activate(struct acpi_processor *pr, case ACPI_STATE_C3: /* Disable bus master reload */ if (new->type != ACPI_STATE_C3 && pr->flags.bm_check) - acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, 0, - ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, 0); break; } } @@ -198,8 +197,7 @@ acpi_processor_power_activate(struct acpi_processor *pr, case ACPI_STATE_C3: /* Enable bus master reload */ if (old->type != ACPI_STATE_C3 && pr->flags.bm_check) - acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, 1, - ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, 1); break; } @@ -291,12 +289,10 @@ static void acpi_processor_idle(void) pr->power.bm_activity <<= diff; - acpi_get_register(ACPI_BITREG_BUS_MASTER_STATUS, - &bm_status, ACPI_MTX_DO_NOT_LOCK); + acpi_get_register(ACPI_BITREG_BUS_MASTER_STATUS, &bm_status); if (bm_status) { pr->power.bm_activity |= 0x1; - acpi_set_register(ACPI_BITREG_BUS_MASTER_STATUS, - 1, ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_BUS_MASTER_STATUS, 1); } /* * PIIX4 Erratum #18: Note that BM_STS doesn't always reflect @@ -411,8 +407,7 @@ static void acpi_processor_idle(void) * All CPUs are trying to go to C3 * Disable bus master arbitration */ - acpi_set_register(ACPI_BITREG_ARB_DISABLE, 1, - ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_ARB_DISABLE, 1); } } else { /* SMP with no shared cache... Invalidate cache */ @@ -428,8 +423,7 @@ static void acpi_processor_idle(void) if (pr->flags.bm_check) { /* Enable bus master arbitration */ atomic_dec(&c3_cpu_count); - acpi_set_register(ACPI_BITREG_ARB_DISABLE, 0, - ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_ARB_DISABLE, 0); } #ifdef CONFIG_GENERIC_TIME @@ -890,8 +884,7 @@ static void acpi_processor_power_verify_c3(struct acpi_processor *pr, " for C3 to be enabled on SMP systems\n")); return; } - acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, - 0, ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, 0); } /* diff --git a/include/acpi/achware.h b/include/acpi/achware.h index f3e9a03..ae449f2 100644 --- a/include/acpi/achware.h +++ b/include/acpi/achware.h @@ -82,7 +82,7 @@ acpi_hw_low_level_read(u32 width, acpi_status acpi_hw_low_level_write(u32 width, u32 value, struct acpi_generic_address *reg); -acpi_status acpi_hw_clear_acpi_status(u32 flags); +acpi_status acpi_hw_clear_acpi_status(void); /* * hwgpe - GPE support diff --git a/include/acpi/acpixf.h b/include/acpi/acpixf.h index f4b0a81..9c26400 100644 --- a/include/acpi/acpixf.h +++ b/include/acpi/acpixf.h @@ -312,9 +312,9 @@ acpi_resource_to_address64(struct acpi_resource *resource, /* * Hardware (ACPI device) interfaces */ -acpi_status acpi_get_register(u32 register_id, u32 * return_value, u32 flags); +acpi_status acpi_get_register(u32 register_id, u32 * return_value); -acpi_status acpi_set_register(u32 register_id, u32 value, u32 flags); +acpi_status acpi_set_register(u32 register_id, u32 value); acpi_status acpi_set_firmware_waking_vector(acpi_physical_address physical_address); -- cgit v0.10.2 From 310a7f7fee489b7dadd27b0d8487bd0ce66281e7 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Use faster ByIndex interface to get FACS Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index 3bacede..545f934 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c @@ -347,8 +347,8 @@ acpi_status acpi_ev_init_global_lock_handler(void) ACPI_FUNCTION_TRACE(ev_init_global_lock_handler); status = - acpi_get_table(ACPI_SIG_FACS, 0, - (struct acpi_table_header **)&facs); + acpi_get_table_by_index(ACPI_TABLE_INDEX_FACS, + (struct acpi_table_header **)&facs); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } -- cgit v0.10.2 From f70a5e7b6c28e0b08f721204f4b98c5d1cfb44d9 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: On AML mutex force-release, set depth to zero (was 1). Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/executer/exmutex.c b/drivers/acpi/executer/exmutex.c index f1dd1b0..b0be2f4 100644 --- a/drivers/acpi/executer/exmutex.c +++ b/drivers/acpi/executer/exmutex.c @@ -329,6 +329,12 @@ acpi_ex_release_mutex(union acpi_operand_object *obj_desc, * * DESCRIPTION: Release all mutexes held by this thread * + * NOTE: This function is called as the thread is exiting the interpreter. + * Mutexes are not released when an individual control method is exited, but + * only when the parent thread actually exits the interpreter. This allows one + * method to acquire a mutex, and a different method to release it, as long as + * this is performed underneath a single parent control method. + * ******************************************************************************/ void acpi_ex_release_all_mutexes(struct acpi_thread_state *thread) @@ -346,7 +352,7 @@ void acpi_ex_release_all_mutexes(struct acpi_thread_state *thread) obj_desc->mutex.prev = NULL; obj_desc->mutex.next = NULL; - obj_desc->mutex.acquisition_depth = 1; + obj_desc->mutex.acquisition_depth = 0; /* Release the mutex, special case for Global Lock */ -- cgit v0.10.2 From 867c9aec576e0c0d89dfa3922019320619002129 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Update interpreter error paths to always report the error Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dswexec.c b/drivers/acpi/dispatcher/dswexec.c index d7a616c..b5b8f16 100644 --- a/drivers/acpi/dispatcher/dswexec.c +++ b/drivers/acpi/dispatcher/dswexec.c @@ -219,7 +219,7 @@ acpi_ds_exec_begin_op(struct acpi_walk_state *walk_state, if (!op) { status = acpi_ds_load2_begin_op(walk_state, out_op); if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + goto error_exit; } op = *out_op; @@ -238,7 +238,7 @@ acpi_ds_exec_begin_op(struct acpi_walk_state *walk_state, status = acpi_ds_scope_stack_pop(walk_state); if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + goto error_exit; } } } @@ -287,7 +287,7 @@ acpi_ds_exec_begin_op(struct acpi_walk_state *walk_state, status = acpi_ds_result_stack_push(walk_state); if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + goto error_exit; } status = acpi_ds_exec_begin_control_op(walk_state, op); @@ -328,6 +328,10 @@ acpi_ds_exec_begin_op(struct acpi_walk_state *walk_state, /* Nothing to do here during method execution */ return_ACPI_STATUS(status); + + error_exit: + status = acpi_ds_method_error(status, walk_state); + return_ACPI_STATUS(status); } /***************************************************************************** -- cgit v0.10.2 From 65e4b9b05dc10ee84b5c9fc3039fbcc6863743d7 Mon Sep 17 00:00:00 2001 From: Fiodor Suietov Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Fix for possible memory leak and fault. Fixed a possible memory leak and fault in acpi_ex_resolve_object_to_value() during a read from a buffer or region field. (BZ 458) Signed-off-by: Bob Moore Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/executer/exresolv.c b/drivers/acpi/executer/exresolv.c index 6499de8..fa17f55 100644 --- a/drivers/acpi/executer/exresolv.c +++ b/drivers/acpi/executer/exresolv.c @@ -141,7 +141,7 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr, acpi_status status = AE_OK; union acpi_operand_object *stack_desc; void *temp_node; - union acpi_operand_object *obj_desc; + union acpi_operand_object *obj_desc = NULL; u16 opcode; ACPI_FUNCTION_TRACE(ex_resolve_object_to_value); @@ -299,8 +299,6 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr, status = acpi_ds_get_package_arguments(stack_desc); break; - /* These cases may never happen here, but just in case.. */ - case ACPI_TYPE_BUFFER_FIELD: case ACPI_TYPE_LOCAL_REGION_FIELD: case ACPI_TYPE_LOCAL_BANK_FIELD: @@ -314,6 +312,10 @@ acpi_ex_resolve_object_to_value(union acpi_operand_object **stack_ptr, status = acpi_ex_read_data_from_field(walk_state, stack_desc, &obj_desc); + + /* Remove a reference to the original operand, then override */ + + acpi_ut_remove_reference(*stack_ptr); *stack_ptr = (void *)obj_desc; break; -- cgit v0.10.2 From cb219bb6bf6f8cabdf07fbbca8487eee5a91ff05 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Add new subsystem state bit that is set after SubsystemInitialize is called Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/utilities/utxface.c b/drivers/acpi/utilities/utxface.c index bec0f54..0a3202d 100644 --- a/drivers/acpi/utilities/utxface.c +++ b/drivers/acpi/utilities/utxface.c @@ -67,6 +67,7 @@ acpi_status acpi_initialize_subsystem(void) ACPI_FUNCTION_TRACE(acpi_initialize_subsystem); + acpi_gbl_startup_flags = ACPI_SUBSYSTEM_INITIALIZE; ACPI_DEBUG_EXEC(acpi_ut_init_stack_ptr_trace()); /* Initialize the OS-Dependent layer */ diff --git a/include/acpi/actypes.h b/include/acpi/actypes.h index fe9eb0e..6fa3f2a 100644 --- a/include/acpi/actypes.h +++ b/include/acpi/actypes.h @@ -412,7 +412,8 @@ typedef u64 acpi_integer; /* * Initialization state */ -#define ACPI_INITIALIZED_OK 0x01 +#define ACPI_SUBSYSTEM_INITIALIZE 0x01 +#define ACPI_INITIALIZED_OK 0x02 /* * Power state values -- cgit v0.10.2 From 2b705a8abbce1753c1e5af5ae2ed97e374277654 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Update version to 20060927 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index 7b02a13..bd5560b 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20060912 +#define ACPI_CA_VERSION 0x20060927 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, -- cgit v0.10.2 From 4d0b4af958453afe871022e44abd57fac09baf67 Mon Sep 17 00:00:00 2001 From: Mikhail Kouzmich Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Restructured module into multiple functions. Restructured the AML ParseLoop function, breaking it into several subfunctions in order to reduce CPU stack use and improve maintainability Signed-off-by: Bob Moore Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/parser/psloop.c b/drivers/acpi/parser/psloop.c index e1541db..a83be52 100644 --- a/drivers/acpi/parser/psloop.c +++ b/drivers/acpi/parser/psloop.c @@ -42,12 +42,11 @@ */ /* - * Parse the AML and build an operation tree as most interpreters, - * like Perl, do. Parsing is done by hand rather than with a YACC - * generated parser to tightly constrain stack and dynamic memory - * usage. At the same time, parsing is kept flexible and the code - * fairly compact by parsing based on a list of AML opcode - * templates in aml_op_info[] + * Parse the AML and build an operation tree as most interpreters, (such as + * Perl) do. Parsing is done by hand rather than with a YACC generated parser + * to tightly constrain stack and dynamic memory usage. Parsing is kept + * flexible and the code fairly compact by parsing based on a list of AML + * opcode templates in aml_op_info[]. */ #include @@ -60,6 +59,761 @@ ACPI_MODULE_NAME("psloop") static u32 acpi_gbl_depth = 0; +/* Local prototypes */ + +static acpi_status acpi_ps_get_aml_opcode(struct acpi_walk_state *walk_state); + +static acpi_status +acpi_ps_build_named_op(struct acpi_walk_state *walk_state, + u8 * aml_op_start, + union acpi_parse_object *unnamed_op, + union acpi_parse_object **op); + +static acpi_status +acpi_ps_create_op(struct acpi_walk_state *walk_state, + u8 * aml_op_start, union acpi_parse_object **new_op); + +static acpi_status +acpi_ps_get_arguments(struct acpi_walk_state *walk_state, + u8 * aml_op_start, union acpi_parse_object *op); + +static acpi_status +acpi_ps_complete_op(struct acpi_walk_state *walk_state, + union acpi_parse_object **op, acpi_status status); + +static acpi_status +acpi_ps_complete_final_op(struct acpi_walk_state *walk_state, + union acpi_parse_object *op, acpi_status status); + +/******************************************************************************* + * + * FUNCTION: acpi_ps_get_aml_opcode + * + * PARAMETERS: walk_state - Current state + * + * RETURN: Status + * + * DESCRIPTION: Extract the next AML opcode from the input stream. + * + ******************************************************************************/ + +static acpi_status acpi_ps_get_aml_opcode(struct acpi_walk_state *walk_state) +{ + + ACPI_FUNCTION_TRACE_PTR(ps_get_aml_opcode, walk_state); + + walk_state->aml_offset = + (u32) ACPI_PTR_DIFF(walk_state->parser_state.aml, + walk_state->parser_state.aml_start); + walk_state->opcode = acpi_ps_peek_opcode(&(walk_state->parser_state)); + + /* + * First cut to determine what we have found: + * 1) A valid AML opcode + * 2) A name string + * 3) An unknown/invalid opcode + */ + walk_state->op_info = acpi_ps_get_opcode_info(walk_state->opcode); + + switch (walk_state->op_info->class) { + case AML_CLASS_ASCII: + case AML_CLASS_PREFIX: + /* + * Starts with a valid prefix or ASCII char, this is a name + * string. Convert the bare name string to a namepath. + */ + walk_state->opcode = AML_INT_NAMEPATH_OP; + walk_state->arg_types = ARGP_NAMESTRING; + break; + + case AML_CLASS_UNKNOWN: + + /* The opcode is unrecognized. Just skip unknown opcodes */ + + ACPI_ERROR((AE_INFO, + "Found unknown opcode %X at AML address %p offset %X, ignoring", + walk_state->opcode, walk_state->parser_state.aml, + walk_state->aml_offset)); + + ACPI_DUMP_BUFFER(walk_state->parser_state.aml, 128); + + /* Assume one-byte bad opcode */ + + walk_state->parser_state.aml++; + return_ACPI_STATUS(AE_CTRL_PARSE_CONTINUE); + + default: + + /* Found opcode info, this is a normal opcode */ + + walk_state->parser_state.aml += + acpi_ps_get_opcode_size(walk_state->opcode); + walk_state->arg_types = walk_state->op_info->parse_args; + break; + } + + return_ACPI_STATUS(AE_OK); +} + +/******************************************************************************* + * + * FUNCTION: acpi_ps_build_named_op + * + * PARAMETERS: walk_state - Current state + * aml_op_start - Begin of named Op in AML + * unnamed_op - Early Op (not a named Op) + * Op - Returned Op + * + * RETURN: Status + * + * DESCRIPTION: Parse a named Op + * + ******************************************************************************/ + +static acpi_status +acpi_ps_build_named_op(struct acpi_walk_state *walk_state, + u8 * aml_op_start, + union acpi_parse_object *unnamed_op, + union acpi_parse_object **op) +{ + acpi_status status = AE_OK; + union acpi_parse_object *arg = NULL; + + ACPI_FUNCTION_TRACE_PTR(ps_build_named_op, walk_state); + + unnamed_op->common.value.arg = NULL; + unnamed_op->common.aml_opcode = walk_state->opcode; + + /* + * Get and append arguments until we find the node that contains + * the name (the type ARGP_NAME). + */ + while (GET_CURRENT_ARG_TYPE(walk_state->arg_types) && + (GET_CURRENT_ARG_TYPE(walk_state->arg_types) != ARGP_NAME)) { + status = + acpi_ps_get_next_arg(walk_state, + &(walk_state->parser_state), + GET_CURRENT_ARG_TYPE(walk_state-> + arg_types), &arg); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + + acpi_ps_append_arg(unnamed_op, arg); + INCREMENT_ARG_LIST(walk_state->arg_types); + } + + /* + * Make sure that we found a NAME and didn't run out of arguments + */ + if (!GET_CURRENT_ARG_TYPE(walk_state->arg_types)) { + return_ACPI_STATUS(AE_AML_NO_OPERAND); + } + + /* We know that this arg is a name, move to next arg */ + + INCREMENT_ARG_LIST(walk_state->arg_types); + + /* + * Find the object. This will either insert the object into + * the namespace or simply look it up + */ + walk_state->op = NULL; + + status = walk_state->descending_callback(walk_state, op); + if (ACPI_FAILURE(status)) { + ACPI_EXCEPTION((AE_INFO, status, "During name lookup/catalog")); + return_ACPI_STATUS(status); + } + + if (!op) { + return_ACPI_STATUS(AE_CTRL_PARSE_CONTINUE); + } + + status = acpi_ps_next_parse_state(walk_state, *op, status); + if (ACPI_FAILURE(status)) { + if (status == AE_CTRL_PENDING) { + return_ACPI_STATUS(AE_CTRL_PARSE_PENDING); + } + return_ACPI_STATUS(status); + } + + acpi_ps_append_arg(*op, unnamed_op->common.value.arg); + acpi_gbl_depth++; + + if ((*op)->common.aml_opcode == AML_REGION_OP) { + /* + * Defer final parsing of an operation_region body, because we don't + * have enough info in the first pass to parse it correctly (i.e., + * there may be method calls within the term_arg elements of the body.) + * + * However, we must continue parsing because the opregion is not a + * standalone package -- we don't know where the end is at this point. + * + * (Length is unknown until parse of the body complete) + */ + (*op)->named.data = aml_op_start; + (*op)->named.length = 0; + } + + return_ACPI_STATUS(AE_OK); +} + +/******************************************************************************* + * + * FUNCTION: acpi_ps_create_op + * + * PARAMETERS: walk_state - Current state + * aml_op_start - Op start in AML + * new_op - Returned Op + * + * RETURN: Status + * + * DESCRIPTION: Get Op from AML + * + ******************************************************************************/ + +static acpi_status +acpi_ps_create_op(struct acpi_walk_state *walk_state, + u8 * aml_op_start, union acpi_parse_object **new_op) +{ + acpi_status status = AE_OK; + union acpi_parse_object *op; + union acpi_parse_object *named_op = NULL; + + ACPI_FUNCTION_TRACE_PTR(ps_create_op, walk_state); + + status = acpi_ps_get_aml_opcode(walk_state); + if (status == AE_CTRL_PARSE_CONTINUE) { + return_ACPI_STATUS(AE_CTRL_PARSE_CONTINUE); + } + + /* Create Op structure and append to parent's argument list */ + + walk_state->op_info = acpi_ps_get_opcode_info(walk_state->opcode); + op = acpi_ps_alloc_op(walk_state->opcode); + if (!op) { + return_ACPI_STATUS(AE_NO_MEMORY); + } + + if (walk_state->op_info->flags & AML_NAMED) { + status = + acpi_ps_build_named_op(walk_state, aml_op_start, op, + &named_op); + acpi_ps_free_op(op); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + + *new_op = named_op; + return_ACPI_STATUS(AE_OK); + } + + /* Not a named opcode, just allocate Op and append to parent */ + + if (walk_state->op_info->flags & AML_CREATE) { + /* + * Backup to beginning of create_xXXfield declaration + * body_length is unknown until we parse the body + */ + op->named.data = aml_op_start; + op->named.length = 0; + } + + acpi_ps_append_arg(acpi_ps_get_parent_scope + (&(walk_state->parser_state)), op); + + if (walk_state->descending_callback != NULL) { + /* + * Find the object. This will either insert the object into + * the namespace or simply look it up + */ + walk_state->op = *new_op = op; + + status = walk_state->descending_callback(walk_state, &op); + status = acpi_ps_next_parse_state(walk_state, op, status); + if (status == AE_CTRL_PENDING) { + status = AE_CTRL_PARSE_PENDING; + } + } + + return_ACPI_STATUS(status); +} + +/******************************************************************************* + * + * FUNCTION: acpi_ps_get_arguments + * + * PARAMETERS: walk_state - Current state + * aml_op_start - Op start in AML + * Op - Current Op + * + * RETURN: Status + * + * DESCRIPTION: Get arguments for passed Op. + * + ******************************************************************************/ + +static acpi_status +acpi_ps_get_arguments(struct acpi_walk_state *walk_state, + u8 * aml_op_start, union acpi_parse_object *op) +{ + acpi_status status = AE_OK; + union acpi_parse_object *arg = NULL; + + ACPI_FUNCTION_TRACE_PTR(ps_get_arguments, walk_state); + + switch (op->common.aml_opcode) { + case AML_BYTE_OP: /* AML_BYTEDATA_ARG */ + case AML_WORD_OP: /* AML_WORDDATA_ARG */ + case AML_DWORD_OP: /* AML_DWORDATA_ARG */ + case AML_QWORD_OP: /* AML_QWORDATA_ARG */ + case AML_STRING_OP: /* AML_ASCIICHARLIST_ARG */ + + /* Fill in constant or string argument directly */ + + acpi_ps_get_next_simple_arg(&(walk_state->parser_state), + GET_CURRENT_ARG_TYPE(walk_state-> + arg_types), + op); + break; + + case AML_INT_NAMEPATH_OP: /* AML_NAMESTRING_ARG */ + + status = + acpi_ps_get_next_namepath(walk_state, + &(walk_state->parser_state), op, + 1); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + + walk_state->arg_types = 0; + break; + + default: + /* + * Op is not a constant or string, append each argument to the Op + */ + while (GET_CURRENT_ARG_TYPE(walk_state->arg_types) + && !walk_state->arg_count) { + walk_state->aml_offset = + (u32) ACPI_PTR_DIFF(walk_state->parser_state.aml, + walk_state->parser_state. + aml_start); + + status = + acpi_ps_get_next_arg(walk_state, + &(walk_state->parser_state), + GET_CURRENT_ARG_TYPE + (walk_state->arg_types), &arg); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + + if (arg) { + arg->common.aml_offset = walk_state->aml_offset; + acpi_ps_append_arg(op, arg); + } + + INCREMENT_ARG_LIST(walk_state->arg_types); + } + + /* Special processing for certain opcodes */ + + /* TBD (remove): Temporary mechanism to disable this code if needed */ + +#ifdef ACPI_ENABLE_MODULE_LEVEL_CODE + + if ((walk_state->pass_number <= ACPI_IMODE_LOAD_PASS1) && + ((walk_state->parse_flags & ACPI_PARSE_DISASSEMBLE) == 0)) { + /* + * We want to skip If/Else/While constructs during Pass1 because we + * want to actually conditionally execute the code during Pass2. + * + * Except for disassembly, where we always want to walk the + * If/Else/While packages + */ + switch (op->common.aml_opcode) { + case AML_IF_OP: + case AML_ELSE_OP: + case AML_WHILE_OP: + + ACPI_DEBUG_PRINT((ACPI_DB_PARSE, + "Pass1: Skipping an If/Else/While body\n")); + + /* Skip body of if/else/while in pass 1 */ + + walk_state->parser_state.aml = + walk_state->parser_state.pkg_end; + walk_state->arg_count = 0; + break; + + default: + break; + } + } +#endif + + switch (op->common.aml_opcode) { + case AML_METHOD_OP: + /* + * Skip parsing of control method because we don't have enough + * info in the first pass to parse it correctly. + * + * Save the length and address of the body + */ + op->named.data = walk_state->parser_state.aml; + op->named.length = (u32) + (walk_state->parser_state.pkg_end - + walk_state->parser_state.aml); + + /* Skip body of method */ + + walk_state->parser_state.aml = + walk_state->parser_state.pkg_end; + walk_state->arg_count = 0; + break; + + case AML_BUFFER_OP: + case AML_PACKAGE_OP: + case AML_VAR_PACKAGE_OP: + + if ((op->common.parent) && + (op->common.parent->common.aml_opcode == + AML_NAME_OP) + && (walk_state->pass_number <= + ACPI_IMODE_LOAD_PASS2)) { + /* + * Skip parsing of Buffers and Packages because we don't have + * enough info in the first pass to parse them correctly. + */ + op->named.data = aml_op_start; + op->named.length = (u32) + (walk_state->parser_state.pkg_end - + aml_op_start); + + /* Skip body */ + + walk_state->parser_state.aml = + walk_state->parser_state.pkg_end; + walk_state->arg_count = 0; + } + break; + + case AML_WHILE_OP: + + if (walk_state->control_state) { + walk_state->control_state->control.package_end = + walk_state->parser_state.pkg_end; + } + break; + + default: + + /* No action for all other opcodes */ + break; + } + + break; + } + + return_ACPI_STATUS(AE_OK); +} + +/******************************************************************************* + * + * FUNCTION: acpi_ps_complete_op + * + * PARAMETERS: walk_state - Current state + * Op - Returned Op + * Status - Parse status before complete Op + * + * RETURN: Status + * + * DESCRIPTION: Complete Op + * + ******************************************************************************/ + +static acpi_status +acpi_ps_complete_op(struct acpi_walk_state *walk_state, + union acpi_parse_object **op, acpi_status status) +{ + acpi_status status2; + + ACPI_FUNCTION_TRACE_PTR(ps_complete_op, walk_state); + + /* + * Finished one argument of the containing scope + */ + walk_state->parser_state.scope->parse_scope.arg_count--; + + /* Close this Op (will result in parse subtree deletion) */ + + status2 = acpi_ps_complete_this_op(walk_state, *op); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + + *op = NULL; + + switch (status) { + case AE_OK: + break; + + case AE_CTRL_TRANSFER: + + /* We are about to transfer to a called method */ + + walk_state->prev_op = NULL; + walk_state->prev_arg_types = walk_state->arg_types; + return_ACPI_STATUS(status); + + case AE_CTRL_END: + + acpi_ps_pop_scope(&(walk_state->parser_state), op, + &walk_state->arg_types, + &walk_state->arg_count); + + if (*op) { + walk_state->op = *op; + walk_state->op_info = + acpi_ps_get_opcode_info((*op)->common.aml_opcode); + walk_state->opcode = (*op)->common.aml_opcode; + + status = walk_state->ascending_callback(walk_state); + status = + acpi_ps_next_parse_state(walk_state, *op, status); + + status2 = acpi_ps_complete_this_op(walk_state, *op); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + } + + status = AE_OK; + break; + + case AE_CTRL_BREAK: + case AE_CTRL_CONTINUE: + + /* Pop off scopes until we find the While */ + + while (!(*op) || ((*op)->common.aml_opcode != AML_WHILE_OP)) { + acpi_ps_pop_scope(&(walk_state->parser_state), op, + &walk_state->arg_types, + &walk_state->arg_count); + + if ((*op)->common.aml_opcode != AML_WHILE_OP) { + status2 = acpi_ds_result_stack_pop(walk_state); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + } + } + + /* Close this iteration of the While loop */ + + walk_state->op = *op; + walk_state->op_info = + acpi_ps_get_opcode_info((*op)->common.aml_opcode); + walk_state->opcode = (*op)->common.aml_opcode; + + status = walk_state->ascending_callback(walk_state); + status = acpi_ps_next_parse_state(walk_state, *op, status); + + status2 = acpi_ps_complete_this_op(walk_state, *op); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + + status = AE_OK; + break; + + case AE_CTRL_TERMINATE: + + /* Clean up */ + do { + if (*op) { + status2 = + acpi_ps_complete_this_op(walk_state, *op); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + status2 = acpi_ds_result_stack_pop(walk_state); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + + acpi_ut_delete_generic_state + (acpi_ut_pop_generic_state + (&walk_state->control_state)); + } + + acpi_ps_pop_scope(&(walk_state->parser_state), op, + &walk_state->arg_types, + &walk_state->arg_count); + + } while (*op); + + return_ACPI_STATUS(AE_OK); + + default: /* All other non-AE_OK status */ + + do { + if (*op) { + status2 = + acpi_ps_complete_this_op(walk_state, *op); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + } + + acpi_ps_pop_scope(&(walk_state->parser_state), op, + &walk_state->arg_types, + &walk_state->arg_count); + + } while (*op); + +#if 0 + /* + * TBD: Cleanup parse ops on error + */ + if (*op == NULL) { + acpi_ps_pop_scope(parser_state, op, + &walk_state->arg_types, + &walk_state->arg_count); + } +#endif + walk_state->prev_op = NULL; + walk_state->prev_arg_types = walk_state->arg_types; + return_ACPI_STATUS(status); + } + + /* This scope complete? */ + + if (acpi_ps_has_completed_scope(&(walk_state->parser_state))) { + acpi_ps_pop_scope(&(walk_state->parser_state), op, + &walk_state->arg_types, + &walk_state->arg_count); + ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "Popped scope, Op=%p\n", *op)); + } else { + *op = NULL; + } + + return_ACPI_STATUS(AE_OK); +} + +/******************************************************************************* + * + * FUNCTION: acpi_ps_complete_final_op + * + * PARAMETERS: walk_state - Current state + * Op - Current Op + * Status - Current parse status before complete last + * Op + * + * RETURN: Status + * + * DESCRIPTION: Complete last Op. + * + ******************************************************************************/ + +static acpi_status +acpi_ps_complete_final_op(struct acpi_walk_state *walk_state, + union acpi_parse_object *op, acpi_status status) +{ + acpi_status status2; + + ACPI_FUNCTION_TRACE_PTR(ps_complete_final_op, walk_state); + + /* + * Complete the last Op (if not completed), and clear the scope stack. + * It is easily possible to end an AML "package" with an unbounded number + * of open scopes (such as when several ASL blocks are closed with + * sequential closing braces). We want to terminate each one cleanly. + */ + ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "AML package complete at Op %p\n", + op)); + do { + if (op) { + if (walk_state->ascending_callback != NULL) { + walk_state->op = op; + walk_state->op_info = + acpi_ps_get_opcode_info(op->common. + aml_opcode); + walk_state->opcode = op->common.aml_opcode; + + status = + walk_state->ascending_callback(walk_state); + status = + acpi_ps_next_parse_state(walk_state, op, + status); + if (status == AE_CTRL_PENDING) { + status = + acpi_ps_complete_op(walk_state, &op, + AE_OK); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + } + + if (status == AE_CTRL_TERMINATE) { + status = AE_OK; + + /* Clean up */ + do { + if (op) { + status2 = + acpi_ps_complete_this_op + (walk_state, op); + if (ACPI_FAILURE + (status2)) { + return_ACPI_STATUS + (status2); + } + } + + acpi_ps_pop_scope(& + (walk_state-> + parser_state), + &op, + &walk_state-> + arg_types, + &walk_state-> + arg_count); + + } while (op); + + return_ACPI_STATUS(status); + } + + else if (ACPI_FAILURE(status)) { + + /* First error is most important */ + + (void) + acpi_ps_complete_this_op(walk_state, + op); + return_ACPI_STATUS(status); + } + } + + status2 = acpi_ps_complete_this_op(walk_state, op); + if (ACPI_FAILURE(status2)) { + return_ACPI_STATUS(status2); + } + } + + acpi_ps_pop_scope(&(walk_state->parser_state), &op, + &walk_state->arg_types, + &walk_state->arg_count); + + } while (op); + + return_ACPI_STATUS(status); +} + /******************************************************************************* * * FUNCTION: acpi_ps_parse_loop @@ -76,10 +830,7 @@ static u32 acpi_gbl_depth = 0; acpi_status acpi_ps_parse_loop(struct acpi_walk_state *walk_state) { acpi_status status = AE_OK; - acpi_status status2; union acpi_parse_object *op = NULL; /* current op */ - union acpi_parse_object *arg = NULL; - union acpi_parse_object *pre_op = NULL; struct acpi_parse_state *parser_state; u8 *aml_op_start = NULL; @@ -128,6 +879,7 @@ acpi_status acpi_ps_parse_loop(struct acpi_walk_state *walk_state) "Invoked method did not return a value")); } + ACPI_EXCEPTION((AE_INFO, status, "GetPredicate Failed")); return_ACPI_STATUS(status); @@ -147,228 +899,36 @@ acpi_status acpi_ps_parse_loop(struct acpi_walk_state *walk_state) /* We were in the middle of an op */ - op = walk_state->prev_op; - walk_state->arg_types = walk_state->prev_arg_types; - } - } -#endif - - /* Iterative parsing loop, while there is more AML to process: */ - - while ((parser_state->aml < parser_state->aml_end) || (op)) { - aml_op_start = parser_state->aml; - if (!op) { - - /* Get the next opcode from the AML stream */ - - walk_state->aml_offset = - (u32) ACPI_PTR_DIFF(parser_state->aml, - parser_state->aml_start); - walk_state->opcode = acpi_ps_peek_opcode(parser_state); - - /* - * First cut to determine what we have found: - * 1) A valid AML opcode - * 2) A name string - * 3) An unknown/invalid opcode - */ - walk_state->op_info = - acpi_ps_get_opcode_info(walk_state->opcode); - switch (walk_state->op_info->class) { - case AML_CLASS_ASCII: - case AML_CLASS_PREFIX: - /* - * Starts with a valid prefix or ASCII char, this is a name - * string. Convert the bare name string to a namepath. - */ - walk_state->opcode = AML_INT_NAMEPATH_OP; - walk_state->arg_types = ARGP_NAMESTRING; - break; - - case AML_CLASS_UNKNOWN: - - /* The opcode is unrecognized. Just skip unknown opcodes */ - - ACPI_ERROR((AE_INFO, - "Found unknown opcode %X at AML address %p offset %X, ignoring", - walk_state->opcode, - parser_state->aml, - walk_state->aml_offset)); - - ACPI_DUMP_BUFFER(parser_state->aml, 128); - - /* Assume one-byte bad opcode */ - - parser_state->aml++; - continue; - - default: - - /* Found opcode info, this is a normal opcode */ - - parser_state->aml += - acpi_ps_get_opcode_size(walk_state->opcode); - walk_state->arg_types = - walk_state->op_info->parse_args; - break; - } - - /* Create Op structure and append to parent's argument list */ - - if (walk_state->op_info->flags & AML_NAMED) { - - /* Allocate a new pre_op if necessary */ - - if (!pre_op) { - pre_op = - acpi_ps_alloc_op(walk_state-> - opcode); - if (!pre_op) { - status = AE_NO_MEMORY; - goto close_this_op; - } - } - - pre_op->common.value.arg = NULL; - pre_op->common.aml_opcode = walk_state->opcode; - - /* - * Get and append arguments until we find the node that contains - * the name (the type ARGP_NAME). - */ - while (GET_CURRENT_ARG_TYPE - (walk_state->arg_types) - && - (GET_CURRENT_ARG_TYPE - (walk_state->arg_types) != ARGP_NAME)) { - status = - acpi_ps_get_next_arg(walk_state, - parser_state, - GET_CURRENT_ARG_TYPE - (walk_state-> - arg_types), - &arg); - if (ACPI_FAILURE(status)) { - goto close_this_op; - } - - acpi_ps_append_arg(pre_op, arg); - INCREMENT_ARG_LIST(walk_state-> - arg_types); - } - - /* - * Make sure that we found a NAME and didn't run out of - * arguments - */ - if (!GET_CURRENT_ARG_TYPE - (walk_state->arg_types)) { - status = AE_AML_NO_OPERAND; - goto close_this_op; - } - - /* We know that this arg is a name, move to next arg */ - - INCREMENT_ARG_LIST(walk_state->arg_types); - - /* - * Find the object. This will either insert the object into - * the namespace or simply look it up - */ - walk_state->op = NULL; + op = walk_state->prev_op; + walk_state->arg_types = walk_state->prev_arg_types; + } + } +#endif - status = - walk_state->descending_callback(walk_state, - &op); - if (ACPI_FAILURE(status)) { - ACPI_EXCEPTION((AE_INFO, status, - "During name lookup/catalog")); - goto close_this_op; - } + /* Iterative parsing loop, while there is more AML to process: */ - if (!op) { + while ((parser_state->aml < parser_state->aml_end) || (op)) { + aml_op_start = parser_state->aml; + if (!op) { + status = + acpi_ps_create_op(walk_state, aml_op_start, &op); + if (ACPI_FAILURE(status)) { + if (status == AE_CTRL_PARSE_CONTINUE) { continue; } - status = - acpi_ps_next_parse_state(walk_state, op, - status); - if (status == AE_CTRL_PENDING) { + if (status == AE_CTRL_PARSE_PENDING) { status = AE_OK; - goto close_this_op; } + status = + acpi_ps_complete_op(walk_state, &op, + status); if (ACPI_FAILURE(status)) { - goto close_this_op; - } - - acpi_ps_append_arg(op, - pre_op->common.value.arg); - acpi_gbl_depth++; - - if (op->common.aml_opcode == AML_REGION_OP) { - /* - * Defer final parsing of an operation_region body, - * because we don't have enough info in the first pass - * to parse it correctly (i.e., there may be method - * calls within the term_arg elements of the body.) - * - * However, we must continue parsing because - * the opregion is not a standalone package -- - * we don't know where the end is at this point. - * - * (Length is unknown until parse of the body complete) - */ - op->named.data = aml_op_start; - op->named.length = 0; - } - } else { - /* Not a named opcode, just allocate Op and append to parent */ - - walk_state->op_info = - acpi_ps_get_opcode_info(walk_state->opcode); - op = acpi_ps_alloc_op(walk_state->opcode); - if (!op) { - status = AE_NO_MEMORY; - goto close_this_op; - } - - if (walk_state->op_info->flags & AML_CREATE) { - /* - * Backup to beginning of create_xXXfield declaration - * body_length is unknown until we parse the body - */ - op->named.data = aml_op_start; - op->named.length = 0; + return_ACPI_STATUS(status); } - acpi_ps_append_arg(acpi_ps_get_parent_scope - (parser_state), op); - - if ((walk_state->descending_callback != NULL)) { - /* - * Find the object. This will either insert the object into - * the namespace or simply look it up - */ - walk_state->op = op; - - status = - walk_state-> - descending_callback(walk_state, - &op); - status = - acpi_ps_next_parse_state(walk_state, - op, - status); - if (status == AE_CTRL_PENDING) { - status = AE_OK; - goto close_this_op; - } - - if (ACPI_FAILURE(status)) { - goto close_this_op; - } - } + continue; } op->common.aml_offset = walk_state->aml_offset; @@ -395,172 +955,17 @@ acpi_status acpi_ps_parse_loop(struct acpi_walk_state *walk_state) /* Get arguments */ - switch (op->common.aml_opcode) { - case AML_BYTE_OP: /* AML_BYTEDATA_ARG */ - case AML_WORD_OP: /* AML_WORDDATA_ARG */ - case AML_DWORD_OP: /* AML_DWORDATA_ARG */ - case AML_QWORD_OP: /* AML_QWORDATA_ARG */ - case AML_STRING_OP: /* AML_ASCIICHARLIST_ARG */ - - /* Fill in constant or string argument directly */ - - acpi_ps_get_next_simple_arg(parser_state, - GET_CURRENT_ARG_TYPE - (walk_state-> - arg_types), op); - break; - - case AML_INT_NAMEPATH_OP: /* AML_NAMESTRING_ARG */ - + status = + acpi_ps_get_arguments(walk_state, aml_op_start, op); + if (ACPI_FAILURE(status)) { status = - acpi_ps_get_next_namepath(walk_state, - parser_state, op, - 1); + acpi_ps_complete_op(walk_state, &op, + status); if (ACPI_FAILURE(status)) { - goto close_this_op; - } - - walk_state->arg_types = 0; - break; - - default: - /* - * Op is not a constant or string, append each argument - * to the Op - */ - while (GET_CURRENT_ARG_TYPE - (walk_state->arg_types) - && !walk_state->arg_count) { - walk_state->aml_offset = (u32) - ACPI_PTR_DIFF(parser_state->aml, - parser_state-> - aml_start); - - status = - acpi_ps_get_next_arg(walk_state, - parser_state, - GET_CURRENT_ARG_TYPE - (walk_state-> - arg_types), - &arg); - if (ACPI_FAILURE(status)) { - goto close_this_op; - } - - if (arg) { - arg->common.aml_offset = - walk_state->aml_offset; - acpi_ps_append_arg(op, arg); - } - INCREMENT_ARG_LIST(walk_state-> - arg_types); - } - - /* Special processing for certain opcodes */ - - /* TBD (remove): Temporary mechanism to disable this code if needed */ - -#ifdef ACPI_ENABLE_MODULE_LEVEL_CODE - - if ((walk_state->pass_number <= - ACPI_IMODE_LOAD_PASS1) - && - ((walk_state-> - parse_flags & ACPI_PARSE_DISASSEMBLE) == - 0)) { - /* - * We want to skip If/Else/While constructs during Pass1 - * because we want to actually conditionally execute the - * code during Pass2. - * - * Except for disassembly, where we always want to - * walk the If/Else/While packages - */ - switch (op->common.aml_opcode) { - case AML_IF_OP: - case AML_ELSE_OP: - case AML_WHILE_OP: - - ACPI_DEBUG_PRINT((ACPI_DB_PARSE, - "Pass1: Skipping an If/Else/While body\n")); - - /* Skip body of if/else/while in pass 1 */ - - parser_state->aml = - parser_state->pkg_end; - walk_state->arg_count = 0; - break; - - default: - break; - } + return_ACPI_STATUS(status); } -#endif - switch (op->common.aml_opcode) { - case AML_METHOD_OP: - - /* - * Skip parsing of control method - * because we don't have enough info in the first pass - * to parse it correctly. - * - * Save the length and address of the body - */ - op->named.data = parser_state->aml; - op->named.length = - (u32) (parser_state->pkg_end - - parser_state->aml); - - /* Skip body of method */ - - parser_state->aml = - parser_state->pkg_end; - walk_state->arg_count = 0; - break; - - case AML_BUFFER_OP: - case AML_PACKAGE_OP: - case AML_VAR_PACKAGE_OP: - - if ((op->common.parent) && - (op->common.parent->common. - aml_opcode == AML_NAME_OP) - && (walk_state->pass_number <= - ACPI_IMODE_LOAD_PASS2)) { - /* - * Skip parsing of Buffers and Packages - * because we don't have enough info in the first pass - * to parse them correctly. - */ - op->named.data = aml_op_start; - op->named.length = - (u32) (parser_state-> - pkg_end - - aml_op_start); - - /* Skip body */ - - parser_state->aml = - parser_state->pkg_end; - walk_state->arg_count = 0; - } - break; - - case AML_WHILE_OP: - if (walk_state->control_state) { - walk_state->control_state-> - control.package_end = - parser_state->pkg_end; - } - break; - - default: - - /* No action for all other opcodes */ - break; - } - break; + continue; } } @@ -575,8 +980,16 @@ acpi_status acpi_ps_parse_loop(struct acpi_walk_state *walk_state) walk_state->arg_types, walk_state->arg_count); if (ACPI_FAILURE(status)) { - goto close_this_op; + status = + acpi_ps_complete_op(walk_state, &op, + status); + if (ACPI_FAILURE(status)) { + return_ACPI_STATUS(status); + } + + continue; } + op = NULL; continue; } @@ -628,269 +1041,16 @@ acpi_status acpi_ps_parse_loop(struct acpi_walk_state *walk_state) acpi_ps_next_parse_state(walk_state, op, status); if (status == AE_CTRL_PENDING) { status = AE_OK; - goto close_this_op; } } - close_this_op: - /* - * Finished one argument of the containing scope - */ - parser_state->scope->parse_scope.arg_count--; - - /* Finished with pre_op */ - - if (pre_op) { - acpi_ps_free_op(pre_op); - pre_op = NULL; - } - - /* Close this Op (will result in parse subtree deletion) */ - - status2 = acpi_ps_complete_this_op(walk_state, op); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - op = NULL; - - switch (status) { - case AE_OK: - break; - - case AE_CTRL_TRANSFER: - - /* We are about to transfer to a called method. */ - - walk_state->prev_op = op; - walk_state->prev_arg_types = walk_state->arg_types; - return_ACPI_STATUS(status); - - case AE_CTRL_END: - - acpi_ps_pop_scope(parser_state, &op, - &walk_state->arg_types, - &walk_state->arg_count); - - if (op) { - walk_state->op = op; - walk_state->op_info = - acpi_ps_get_opcode_info(op->common. - aml_opcode); - walk_state->opcode = op->common.aml_opcode; - - status = - walk_state->ascending_callback(walk_state); - status = - acpi_ps_next_parse_state(walk_state, op, - status); - - status2 = - acpi_ps_complete_this_op(walk_state, op); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - op = NULL; - } - status = AE_OK; - break; - - case AE_CTRL_BREAK: - case AE_CTRL_CONTINUE: - - /* Pop off scopes until we find the While */ - - while (!op || (op->common.aml_opcode != AML_WHILE_OP)) { - acpi_ps_pop_scope(parser_state, &op, - &walk_state->arg_types, - &walk_state->arg_count); - - if (op->common.aml_opcode != AML_WHILE_OP) { - status2 = - acpi_ds_result_stack_pop - (walk_state); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - } - } - - /* Close this iteration of the While loop */ - - walk_state->op = op; - walk_state->op_info = - acpi_ps_get_opcode_info(op->common.aml_opcode); - walk_state->opcode = op->common.aml_opcode; - - status = walk_state->ascending_callback(walk_state); - status = - acpi_ps_next_parse_state(walk_state, op, status); - - status2 = acpi_ps_complete_this_op(walk_state, op); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - op = NULL; - - status = AE_OK; - break; - - case AE_CTRL_TERMINATE: - - status = AE_OK; - - /* Clean up */ - do { - if (op) { - status2 = - acpi_ps_complete_this_op(walk_state, - op); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - - status2 = - acpi_ds_result_stack_pop - (walk_state); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - - acpi_ut_delete_generic_state - (acpi_ut_pop_generic_state - (&walk_state->control_state)); - } - - acpi_ps_pop_scope(parser_state, &op, - &walk_state->arg_types, - &walk_state->arg_count); - - } while (op); - - return_ACPI_STATUS(status); - - default: /* All other non-AE_OK status */ - - do { - if (op) { - status2 = - acpi_ps_complete_this_op(walk_state, - op); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - } - - acpi_ps_pop_scope(parser_state, &op, - &walk_state->arg_types, - &walk_state->arg_count); - - } while (op); - - /* - * TBD: Cleanup parse ops on error - */ -#if 0 - if (op == NULL) { - acpi_ps_pop_scope(parser_state, &op, - &walk_state->arg_types, - &walk_state->arg_count); - } -#endif - walk_state->prev_op = op; - walk_state->prev_arg_types = walk_state->arg_types; + status = acpi_ps_complete_op(walk_state, &op, status); + if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } - /* This scope complete? */ - - if (acpi_ps_has_completed_scope(parser_state)) { - acpi_ps_pop_scope(parser_state, &op, - &walk_state->arg_types, - &walk_state->arg_count); - ACPI_DEBUG_PRINT((ACPI_DB_PARSE, - "Popped scope, Op=%p\n", op)); - } else { - op = NULL; - } - } /* while parser_state->Aml */ - /* - * Complete the last Op (if not completed), and clear the scope stack. - * It is easily possible to end an AML "package" with an unbounded number - * of open scopes (such as when several ASL blocks are closed with - * sequential closing braces). We want to terminate each one cleanly. - */ - ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "AML package complete at Op %p\n", - op)); - do { - if (op) { - if (walk_state->ascending_callback != NULL) { - walk_state->op = op; - walk_state->op_info = - acpi_ps_get_opcode_info(op->common. - aml_opcode); - walk_state->opcode = op->common.aml_opcode; - - status = - walk_state->ascending_callback(walk_state); - status = - acpi_ps_next_parse_state(walk_state, op, - status); - if (status == AE_CTRL_PENDING) { - status = AE_OK; - goto close_this_op; - } - - if (status == AE_CTRL_TERMINATE) { - status = AE_OK; - - /* Clean up */ - do { - if (op) { - status2 = - acpi_ps_complete_this_op - (walk_state, op); - if (ACPI_FAILURE - (status2)) { - return_ACPI_STATUS - (status2); - } - } - - acpi_ps_pop_scope(parser_state, - &op, - &walk_state-> - arg_types, - &walk_state-> - arg_count); - - } while (op); - - return_ACPI_STATUS(status); - } - - else if (ACPI_FAILURE(status)) { - - /* First error is most important */ - - (void) - acpi_ps_complete_this_op(walk_state, - op); - return_ACPI_STATUS(status); - } - } - - status2 = acpi_ps_complete_this_op(walk_state, op); - if (ACPI_FAILURE(status2)) { - return_ACPI_STATUS(status2); - } - } - - acpi_ps_pop_scope(parser_state, &op, &walk_state->arg_types, - &walk_state->arg_count); - - } while (op); - + status = acpi_ps_complete_final_op(walk_state, op, status); return_ACPI_STATUS(status); } diff --git a/include/acpi/acexcep.h b/include/acpi/acexcep.h index 797ca1e..8fa00e8 100644 --- a/include/acpi/acexcep.h +++ b/include/acpi/acexcep.h @@ -178,8 +178,10 @@ #define AE_CTRL_BREAK (acpi_status) (0x0009 | AE_CODE_CONTROL) #define AE_CTRL_CONTINUE (acpi_status) (0x000A | AE_CODE_CONTROL) #define AE_CTRL_SKIP (acpi_status) (0x000B | AE_CODE_CONTROL) +#define AE_CTRL_PARSE_CONTINUE (acpi_status) (0x000C | AE_CODE_CONTROL) +#define AE_CTRL_PARSE_PENDING (acpi_status) (0x000D | AE_CODE_CONTROL) -#define AE_CODE_CTRL_MAX 0x000B +#define AE_CODE_CTRL_MAX 0x000D #ifdef DEFINE_ACPI_GLOBALS @@ -291,7 +293,9 @@ char const *acpi_gbl_exception_names_ctrl[] = { "AE_CTRL_TRANSFER", "AE_CTRL_BREAK", "AE_CTRL_CONTINUE", - "AE_CTRL_SKIP" + "AE_CTRL_SKIP", + "AE_CTRL_PARSE_CONTINUE", + "AE_CTRL_PARSE_PENDING" }; #endif /* ACPI GLOBALS */ -- cgit v0.10.2 From 9bc75cff4919f9d947982d805aed89582a20d04d Mon Sep 17 00:00:00 2001 From: Valery Podrezov Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Eliminate control method 2-pass parse/execute. Completed an AML interpreter performance enhancement for control method execution. Previously a 2-pass parse/execution, control methods are now completely parsed and executed in single pass. This improves overall interpreter performance by ~25%, reduces code size, and reduces CPU stack use. Signed-off-by: Bob Moore Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dsmethod.c b/drivers/acpi/dispatcher/dsmethod.c index cf888ad..aa60dca 100644 --- a/drivers/acpi/dispatcher/dsmethod.c +++ b/drivers/acpi/dispatcher/dsmethod.c @@ -327,7 +327,7 @@ acpi_ds_call_control_method(struct acpi_thread_state *thread, ACPI_FUNCTION_TRACE_PTR(ds_call_control_method, this_walk_state); ACPI_DEBUG_PRINT((ACPI_DB_DISPATCH, - "Execute method %p, currentstate=%p\n", + "Calling method %p, currentstate=%p\n", this_walk_state->prev_op, this_walk_state)); /* @@ -351,49 +351,7 @@ acpi_ds_call_control_method(struct acpi_thread_state *thread, return_ACPI_STATUS(status); } - /* - * 1) Parse the method. All "normal" methods are parsed for each execution. - * Internal methods (_OSI, etc.) do not require parsing. - */ - if (!(obj_desc->method.method_flags & AML_METHOD_INTERNAL_ONLY)) { - - /* Create a new walk state for the parse */ - - next_walk_state = - acpi_ds_create_walk_state(obj_desc->method.owner_id, op, - obj_desc, NULL); - if (!next_walk_state) { - status = AE_NO_MEMORY; - goto cleanup; - } - - /* Create and init a parse tree root */ - - op = acpi_ps_create_scope_op(); - if (!op) { - status = AE_NO_MEMORY; - goto cleanup; - } - - status = acpi_ds_init_aml_walk(next_walk_state, op, method_node, - obj_desc->method.aml_start, - obj_desc->method.aml_length, - NULL, 1); - if (ACPI_FAILURE(status)) { - acpi_ps_delete_parse_tree(op); - goto cleanup; - } - - /* Begin AML parse (deletes next_walk_state) */ - - status = acpi_ps_parse_aml(next_walk_state); - acpi_ps_delete_parse_tree(op); - if (ACPI_FAILURE(status)) { - goto cleanup; - } - } - - /* 2) Begin method execution. Create a new walk state */ + /* Begin method parse/execution. Create a new walk state */ next_walk_state = acpi_ds_create_walk_state(obj_desc->method.owner_id, NULL, obj_desc, thread); @@ -445,8 +403,8 @@ acpi_ds_call_control_method(struct acpi_thread_state *thread, this_walk_state->num_operands = 0; ACPI_DEBUG_PRINT((ACPI_DB_DISPATCH, - "Starting nested execution, newstate=%p\n", - next_walk_state)); + "**** Begin nested execution of [%4.4s] **** WalkState=%p\n", + method_node->name.ascii, next_walk_state)); /* Invoke an internal method if necessary */ diff --git a/drivers/acpi/parser/psloop.c b/drivers/acpi/parser/psloop.c index a83be52..881687c 100644 --- a/drivers/acpi/parser/psloop.c +++ b/drivers/acpi/parser/psloop.c @@ -226,7 +226,7 @@ acpi_ps_build_named_op(struct acpi_walk_state *walk_state, return_ACPI_STATUS(status); } - if (!op) { + if (!*op) { return_ACPI_STATUS(AE_CTRL_PARSE_CONTINUE); } diff --git a/drivers/acpi/parser/psxface.c b/drivers/acpi/parser/psxface.c index 5d996c1..9069c69 100644 --- a/drivers/acpi/parser/psxface.c +++ b/drivers/acpi/parser/psxface.c @@ -54,8 +54,6 @@ static void acpi_ps_start_trace(struct acpi_evaluate_info *info); static void acpi_ps_stop_trace(struct acpi_evaluate_info *info); -static acpi_status acpi_ps_execute_pass(struct acpi_evaluate_info *info); - static void acpi_ps_update_parameter_list(struct acpi_evaluate_info *info, u16 action); @@ -215,6 +213,8 @@ static void acpi_ps_stop_trace(struct acpi_evaluate_info *info) acpi_status acpi_ps_execute_method(struct acpi_evaluate_info *info) { acpi_status status; + union acpi_parse_object *op; + struct acpi_walk_state *walk_state; ACPI_FUNCTION_TRACE(ps_execute_method); @@ -234,8 +234,7 @@ acpi_status acpi_ps_execute_method(struct acpi_evaluate_info *info) } /* - * The caller "owns" the parameters, so give each one an extra - * reference + * The caller "owns" the parameters, so give each one an extra reference */ acpi_ps_update_parameter_list(info, REF_INCREMENT); @@ -244,30 +243,50 @@ acpi_status acpi_ps_execute_method(struct acpi_evaluate_info *info) acpi_ps_start_trace(info); /* - * 1) Perform the first pass parse of the method to enter any - * named objects that it creates into the namespace + * Execute the method. Performs parse simultaneously */ ACPI_DEBUG_PRINT((ACPI_DB_PARSE, - "**** Begin Method Parse **** Entry=%p obj=%p\n", - info->resolved_node, info->obj_desc)); + "**** Begin Method Parse/Execute [%4.4s] **** Node=%p Obj=%p\n", + info->resolved_node->name.ascii, info->resolved_node, + info->obj_desc)); - info->pass_number = 1; - status = acpi_ps_execute_pass(info); - if (ACPI_FAILURE(status)) { + /* Create and init a Root Node */ + + op = acpi_ps_create_scope_op(); + if (!op) { + status = AE_NO_MEMORY; goto cleanup; } - /* - * 2) Execute the method. Performs second pass parse simultaneously - */ - ACPI_DEBUG_PRINT((ACPI_DB_PARSE, - "**** Begin Method Execution **** Entry=%p obj=%p\n", - info->resolved_node, info->obj_desc)); + /* Create and initialize a new walk state */ info->pass_number = 3; - status = acpi_ps_execute_pass(info); + walk_state = + acpi_ds_create_walk_state(info->obj_desc->method.owner_id, NULL, + NULL, NULL); + if (!walk_state) { + status = AE_NO_MEMORY; + goto cleanup; + } + + status = acpi_ds_init_aml_walk(walk_state, op, info->resolved_node, + info->obj_desc->method.aml_start, + info->obj_desc->method.aml_length, info, + info->pass_number); + if (ACPI_FAILURE(status)) { + acpi_ds_delete_walk_state(walk_state); + goto cleanup; + } + + /* Parse the AML */ + + status = acpi_ps_parse_aml(walk_state); + + /* walk_state was deleted by parse_aml */ cleanup: + acpi_ps_delete_parse_tree(op); + /* End optional tracing */ acpi_ps_stop_trace(info); @@ -330,62 +349,3 @@ acpi_ps_update_parameter_list(struct acpi_evaluate_info *info, u16 action) } } } - -/******************************************************************************* - * - * FUNCTION: acpi_ps_execute_pass - * - * PARAMETERS: Info - See struct acpi_evaluate_info - * (Used: pass_number, Node, and obj_desc) - * - * RETURN: Status - * - * DESCRIPTION: Single AML pass: Parse or Execute a control method - * - ******************************************************************************/ - -static acpi_status acpi_ps_execute_pass(struct acpi_evaluate_info *info) -{ - acpi_status status; - union acpi_parse_object *op; - struct acpi_walk_state *walk_state; - - ACPI_FUNCTION_TRACE(ps_execute_pass); - - /* Create and init a Root Node */ - - op = acpi_ps_create_scope_op(); - if (!op) { - return_ACPI_STATUS(AE_NO_MEMORY); - } - - /* Create and initialize a new walk state */ - - walk_state = - acpi_ds_create_walk_state(info->obj_desc->method.owner_id, NULL, - NULL, NULL); - if (!walk_state) { - status = AE_NO_MEMORY; - goto cleanup; - } - - status = acpi_ds_init_aml_walk(walk_state, op, info->resolved_node, - info->obj_desc->method.aml_start, - info->obj_desc->method.aml_length, - info->pass_number == 1 ? NULL : info, - info->pass_number); - if (ACPI_FAILURE(status)) { - acpi_ds_delete_walk_state(walk_state); - goto cleanup; - } - - /* Parse the AML */ - - status = acpi_ps_parse_aml(walk_state); - - /* Walk state was deleted by parse_aml */ - - cleanup: - acpi_ps_delete_parse_tree(op); - return_ACPI_STATUS(status); -} -- cgit v0.10.2 From d1fdda83f7c567f376ddd4305833de09f7919ca9 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Fix race condition with AcpiWalkNamespace. Fixed a problem with a possible race condition between threads executing AcpiWalkNamespace and the AML interpreter. This condition was removed by modifying AcpiWalkNamespace to (by default) ignore all temporary namespace entries created during any concurrent control method execution Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dswload.c b/drivers/acpi/dispatcher/dswload.c index 565d455..4ed0868 100644 --- a/drivers/acpi/dispatcher/dswload.c +++ b/drivers/acpi/dispatcher/dswload.c @@ -756,9 +756,9 @@ acpi_ds_load2_begin_op(struct acpi_walk_state *walk_state, flags = ACPI_NS_NO_UPSEARCH; if (walk_state->pass_number == 3) { - /* Execution mode, node cannot already exist */ + /* Execution mode, node cannot already exist, node is temporary */ - flags |= ACPI_NS_ERROR_IF_FOUND; + flags |= (ACPI_NS_ERROR_IF_FOUND | ACPI_NS_TEMPORARY); } /* Add new entry or lookup existing entry */ diff --git a/drivers/acpi/namespace/nsdump.c b/drivers/acpi/namespace/nsdump.c index da88834..ec5ce59 100644 --- a/drivers/acpi/namespace/nsdump.c +++ b/drivers/acpi/namespace/nsdump.c @@ -226,6 +226,12 @@ acpi_ns_dump_one_object(acpi_handle obj_handle, obj_desc = acpi_ns_get_attached_object(this_node); acpi_dbg_level = dbg_level; + /* Temp nodes are those nodes created by a control method */ + + if (this_node->flags & ANOBJ_TEMPORARY) { + acpi_os_printf("(T) "); + } + switch (info->display_type & ACPI_DISPLAY_MASK) { case ACPI_DISPLAY_SUMMARY: @@ -623,7 +629,8 @@ acpi_ns_dump_objects(acpi_object_type type, info.display_type = display_type; (void)acpi_ns_walk_namespace(type, start_handle, max_depth, - ACPI_NS_WALK_NO_UNLOCK, + ACPI_NS_WALK_NO_UNLOCK | + ACPI_NS_WALK_TEMP_NODES, acpi_ns_dump_one_object, (void *)&info, NULL); } diff --git a/drivers/acpi/namespace/nssearch.c b/drivers/acpi/namespace/nssearch.c index 566f0a4..d261c9b 100644 --- a/drivers/acpi/namespace/nssearch.c +++ b/drivers/acpi/namespace/nssearch.c @@ -402,6 +402,10 @@ acpi_ns_search_and_enter(u32 target_name, } #endif + if (flags & ACPI_NS_TEMPORARY) { + new_node->flags |= ANOBJ_TEMPORARY; + } + /* Install the new object into the parent's list of children */ acpi_ns_install_node(walk_state, node, new_node, type); diff --git a/drivers/acpi/namespace/nswalk.c b/drivers/acpi/namespace/nswalk.c index c8f6bef..a138fcb 100644 --- a/drivers/acpi/namespace/nswalk.c +++ b/drivers/acpi/namespace/nswalk.c @@ -126,7 +126,7 @@ struct acpi_namespace_node *acpi_ns_get_next_node(acpi_object_type type, * PARAMETERS: Type - acpi_object_type to search for * start_node - Handle in namespace where search begins * max_depth - Depth to which search is to reach - * unlock_before_callback- Whether to unlock the NS before invoking + * Flags - Whether to unlock the NS before invoking * the callback routine * user_function - Called when an object of "Type" is found * Context - Passed to user function @@ -153,7 +153,7 @@ acpi_status acpi_ns_walk_namespace(acpi_object_type type, acpi_handle start_node, u32 max_depth, - u8 unlock_before_callback, + u32 flags, acpi_walk_callback user_function, void *context, void **return_value) { @@ -201,12 +201,15 @@ acpi_ns_walk_namespace(acpi_object_type type, child_type = child_node->type; } - if (child_type == type) { + if ((child_type == type) && + (!(child_node->flags & ANOBJ_TEMPORARY) || + (child_node->flags & ANOBJ_TEMPORARY) + && (flags & ACPI_NS_WALK_TEMP_NODES))) { /* * Found a matching node, invoke the user * callback function */ - if (unlock_before_callback) { + if (flags & ACPI_NS_WALK_UNLOCK) { mutex_status = acpi_ut_release_mutex (ACPI_MTX_NAMESPACE); @@ -219,7 +222,7 @@ acpi_ns_walk_namespace(acpi_object_type type, status = user_function(child_node, level, context, return_value); - if (unlock_before_callback) { + if (flags & ACPI_NS_WALK_UNLOCK) { mutex_status = acpi_ut_acquire_mutex (ACPI_MTX_NAMESPACE); diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index 553763d..287da6f 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -204,7 +204,7 @@ struct acpi_namespace_node { /* Namespace Node flags */ #define ANOBJ_END_OF_PEER_LIST 0x01 /* End-of-list, Peer field points to parent */ -#define ANOBJ_RESERVED 0x02 /* Available for future use */ +#define ANOBJ_TEMPORARY 0x02 /* Node is create by a method and is temporary */ #define ANOBJ_METHOD_ARG 0x04 /* Node is a method argument */ #define ANOBJ_METHOD_LOCAL 0x08 /* Node is a method local */ #define ANOBJ_SUBTREE_HAS_INI 0x10 /* Used to optimize device initialization */ diff --git a/include/acpi/acnamesp.h b/include/acpi/acnamesp.h index b3b9f0e..19a6129 100644 --- a/include/acpi/acnamesp.h +++ b/include/acpi/acnamesp.h @@ -65,9 +65,13 @@ #define ACPI_NS_ERROR_IF_FOUND 0x08 #define ACPI_NS_PREFIX_IS_SCOPE 0x10 #define ACPI_NS_EXTERNAL 0x20 +#define ACPI_NS_TEMPORARY 0x40 -#define ACPI_NS_WALK_UNLOCK TRUE -#define ACPI_NS_WALK_NO_UNLOCK FALSE +/* Flags for acpi_ns_walk_namespace */ + +#define ACPI_NS_WALK_NO_UNLOCK 0 +#define ACPI_NS_WALK_UNLOCK 0x01 +#define ACPI_NS_WALK_TEMP_NODES 0x02 /* * nsinit - Namespace initialization @@ -92,7 +96,7 @@ acpi_status acpi_ns_walk_namespace(acpi_object_type type, acpi_handle start_object, u32 max_depth, - u8 unlock_before_callback, + u32 flags, acpi_walk_callback user_function, void *context, void **return_value); -- cgit v0.10.2 From b7a69806308600711589e4ca306d18dd029ef0cf Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: _CID support for PCI Root Bridge detection. Implemented _CID support for PCI Root Bridge detection. If the _HID does not match the predefined root bridge IDs, the _CID list (if present) is now obtained and also checked for an ID match Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evrgnini.c b/drivers/acpi/events/evrgnini.c index 790d49b..6176602 100644 --- a/drivers/acpi/events/evrgnini.c +++ b/drivers/acpi/events/evrgnini.c @@ -48,6 +48,11 @@ #define _COMPONENT ACPI_EVENTS ACPI_MODULE_NAME("evrgnini") +/* Local prototypes */ +static u8 acpi_ev_match_pci_root_bridge(char *id); + +static u8 acpi_ev_is_pci_root_bridge(struct acpi_namespace_node *node); + /******************************************************************************* * * FUNCTION: acpi_ev_system_memory_region_setup @@ -62,6 +67,7 @@ ACPI_MODULE_NAME("evrgnini") * DESCRIPTION: Setup a system_memory operation region * ******************************************************************************/ + acpi_status acpi_ev_system_memory_region_setup(acpi_handle handle, u32 function, @@ -168,9 +174,9 @@ acpi_ev_pci_config_region_setup(acpi_handle handle, union acpi_operand_object *handler_obj; struct acpi_namespace_node *parent_node; struct acpi_namespace_node *pci_root_node; + struct acpi_namespace_node *pci_device_node; union acpi_operand_object *region_obj = (union acpi_operand_object *)handle; - struct acpi_device_id object_hID; ACPI_FUNCTION_TRACE(ev_pci_config_region_setup); @@ -215,45 +221,30 @@ acpi_ev_pci_config_region_setup(acpi_handle handle, pci_root_node = parent_node; while (pci_root_node != acpi_gbl_root_node) { - status = - acpi_ut_execute_HID(pci_root_node, &object_hID); - if (ACPI_SUCCESS(status)) { - /* - * Got a valid _HID string, check if this is a PCI root. - * New for ACPI 3.0: check for a PCI Express root also. - */ - if (! - (ACPI_STRNCMP - (object_hID.value, PCI_ROOT_HID_STRING, - sizeof(PCI_ROOT_HID_STRING))) - || - !(ACPI_STRNCMP - (object_hID.value, - PCI_EXPRESS_ROOT_HID_STRING, - sizeof(PCI_EXPRESS_ROOT_HID_STRING)))) { - - /* Install a handler for this PCI root bridge */ - status = - acpi_install_address_space_handler((acpi_handle) pci_root_node, ACPI_ADR_SPACE_PCI_CONFIG, ACPI_DEFAULT_HANDLER, NULL, NULL); - if (ACPI_FAILURE(status)) { - if (status == AE_SAME_HANDLER) { - /* - * It is OK if the handler is already installed on the root - * bridge. Still need to return a context object for the - * new PCI_Config operation region, however. - */ - status = AE_OK; - } else { - ACPI_EXCEPTION((AE_INFO, - status, - "Could not install PciConfig handler for Root Bridge %4.4s", - acpi_ut_get_node_name - (pci_root_node))); - } + /* Get the _HID/_CID in order to detect a root_bridge */ + + if (acpi_ev_is_pci_root_bridge(pci_root_node)) { + + /* Install a handler for this PCI root bridge */ + + status = acpi_install_address_space_handler((acpi_handle) pci_root_node, ACPI_ADR_SPACE_PCI_CONFIG, ACPI_DEFAULT_HANDLER, NULL, NULL); + if (ACPI_FAILURE(status)) { + if (status == AE_SAME_HANDLER) { + /* + * It is OK if the handler is already installed on the root + * bridge. Still need to return a context object for the + * new PCI_Config operation region, however. + */ + status = AE_OK; + } else { + ACPI_EXCEPTION((AE_INFO, status, + "Could not install PciConfig handler for Root Bridge %4.4s", + acpi_ut_get_node_name + (pci_root_node))); } - break; } + break; } pci_root_node = acpi_ns_get_parent_node(pci_root_node); @@ -282,14 +273,25 @@ acpi_ev_pci_config_region_setup(acpi_handle handle, /* * For PCI_Config space access, we need the segment, bus, * device and function numbers. Acquire them here. + * + * Find the parent device object. (This allows the operation region to be + * within a subscope under the device, such as a control method.) */ + pci_device_node = region_obj->region.node; + while (pci_device_node && (pci_device_node->type != ACPI_TYPE_DEVICE)) { + pci_device_node = acpi_ns_get_parent_node(pci_device_node); + } + + if (!pci_device_node) { + return_ACPI_STATUS(AE_AML_OPERAND_TYPE); + } /* * Get the PCI device and function numbers from the _ADR object * contained in the parent's scope. */ status = - acpi_ut_evaluate_numeric_object(METHOD_NAME__ADR, parent_node, + acpi_ut_evaluate_numeric_object(METHOD_NAME__ADR, pci_device_node, &pci_value); /* @@ -329,6 +331,91 @@ acpi_ev_pci_config_region_setup(acpi_handle handle, /******************************************************************************* * + * FUNCTION: acpi_ev_match_pci_root_bridge + * + * PARAMETERS: Id - The HID/CID in string format + * + * RETURN: TRUE if the Id is a match for a PCI/PCI-Express Root Bridge + * + * DESCRIPTION: Determine if the input ID is a PCI Root Bridge ID. + * + ******************************************************************************/ + +static u8 acpi_ev_match_pci_root_bridge(char *id) +{ + + /* + * Check if this is a PCI root. + * ACPI 3.0+: check for a PCI Express root also. + */ + if (!(ACPI_STRNCMP(id, + PCI_ROOT_HID_STRING, + sizeof(PCI_ROOT_HID_STRING))) || + !(ACPI_STRNCMP(id, + PCI_EXPRESS_ROOT_HID_STRING, + sizeof(PCI_EXPRESS_ROOT_HID_STRING)))) { + return (TRUE); + } + + return (FALSE); +} + +/******************************************************************************* + * + * FUNCTION: acpi_ev_is_pci_root_bridge + * + * PARAMETERS: Node - Device node being examined + * + * RETURN: TRUE if device is a PCI/PCI-Express Root Bridge + * + * DESCRIPTION: Determine if the input device represents a PCI Root Bridge by + * examining the _HID and _CID for the device. + * + ******************************************************************************/ + +static u8 acpi_ev_is_pci_root_bridge(struct acpi_namespace_node *node) +{ + acpi_status status; + struct acpi_device_id hid; + struct acpi_compatible_id_list *cid; + acpi_native_uint i; + + /* + * Get the _HID and check for a PCI Root Bridge + */ + status = acpi_ut_execute_HID(node, &hid); + if (ACPI_FAILURE(status)) { + return (FALSE); + } + + if (acpi_ev_match_pci_root_bridge(hid.value)) { + return (TRUE); + } + + /* + * The _HID did not match. + * Get the _CID and check for a PCI Root Bridge + */ + status = acpi_ut_execute_CID(node, &cid); + if (ACPI_FAILURE(status)) { + return (FALSE); + } + + /* Check all _CIDs in the returned list */ + + for (i = 0; i < cid->count; i++) { + if (acpi_ev_match_pci_root_bridge(cid->id[i].value)) { + ACPI_FREE(cid); + return (TRUE); + } + } + + ACPI_FREE(cid); + return (FALSE); +} + +/******************************************************************************* + * * FUNCTION: acpi_ev_pci_bar_region_setup * * PARAMETERS: Handle - Region we are interested in -- cgit v0.10.2 From ec3153fb0e96988dc7e378b3ab01e05131ba713b Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Use manifest constants for parse pass number Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dsmethod.c b/drivers/acpi/dispatcher/dsmethod.c index aa60dca..57c5159 100644 --- a/drivers/acpi/dispatcher/dsmethod.c +++ b/drivers/acpi/dispatcher/dsmethod.c @@ -382,7 +382,8 @@ acpi_ds_call_control_method(struct acpi_thread_state *thread, status = acpi_ds_init_aml_walk(next_walk_state, NULL, method_node, obj_desc->method.aml_start, - obj_desc->method.aml_length, info, 3); + obj_desc->method.aml_length, info, + ACPI_IMODE_EXECUTE); ACPI_FREE(info); if (ACPI_FAILURE(status)) { diff --git a/drivers/acpi/dispatcher/dsopcode.c b/drivers/acpi/dispatcher/dsopcode.c index 5b974a8..26035a3 100644 --- a/drivers/acpi/dispatcher/dsopcode.c +++ b/drivers/acpi/dispatcher/dsopcode.c @@ -114,7 +114,7 @@ acpi_ds_execute_arguments(struct acpi_namespace_node *node, } status = acpi_ds_init_aml_walk(walk_state, op, NULL, aml_start, - aml_length, NULL, 1); + aml_length, NULL, ACPI_IMODE_LOAD_PASS1); if (ACPI_FAILURE(status)) { acpi_ds_delete_walk_state(walk_state); goto cleanup; @@ -157,7 +157,7 @@ acpi_ds_execute_arguments(struct acpi_namespace_node *node, /* Execute the opcode and arguments */ status = acpi_ds_init_aml_walk(walk_state, op, NULL, aml_start, - aml_length, NULL, 3); + aml_length, NULL, ACPI_IMODE_EXECUTE); if (ACPI_FAILURE(status)) { acpi_ds_delete_walk_state(walk_state); goto cleanup; diff --git a/drivers/acpi/dispatcher/dswload.c b/drivers/acpi/dispatcher/dswload.c index 4ed0868..baf04e8 100644 --- a/drivers/acpi/dispatcher/dswload.c +++ b/drivers/acpi/dispatcher/dswload.c @@ -754,7 +754,7 @@ acpi_ds_load2_begin_op(struct acpi_walk_state *walk_state, } flags = ACPI_NS_NO_UPSEARCH; - if (walk_state->pass_number == 3) { + if (walk_state->pass_number == ACPI_IMODE_EXECUTE) { /* Execution mode, node cannot already exist, node is temporary */ diff --git a/drivers/acpi/namespace/nsparse.c b/drivers/acpi/namespace/nsparse.c index 2e22479..a68de26 100644 --- a/drivers/acpi/namespace/nsparse.c +++ b/drivers/acpi/namespace/nsparse.c @@ -160,10 +160,10 @@ acpi_ns_parse_table(acpi_native_uint table_index, * each Parser Op subtree is deleted when it is finished. This saves * a great deal of memory, and allows a small cache of parse objects * to service the entire parse. The second pass of the parse then - * performs another complete parse of the AML.. + * performs another complete parse of the AML. */ ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "**** Start pass 1\n")); - status = acpi_ns_one_complete_parse(1, table_index); + status = acpi_ns_one_complete_parse(ACPI_IMODE_LOAD_PASS1, table_index); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } @@ -178,7 +178,7 @@ acpi_ns_parse_table(acpi_native_uint table_index, * parse objects are all cached. */ ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "**** Start pass 2\n")); - status = acpi_ns_one_complete_parse(2, table_index); + status = acpi_ns_one_complete_parse(ACPI_IMODE_LOAD_PASS2, table_index); if (ACPI_FAILURE(status)) { return_ACPI_STATUS(status); } diff --git a/drivers/acpi/parser/psxface.c b/drivers/acpi/parser/psxface.c index 9069c69..fc5b3e5 100644 --- a/drivers/acpi/parser/psxface.c +++ b/drivers/acpi/parser/psxface.c @@ -260,7 +260,7 @@ acpi_status acpi_ps_execute_method(struct acpi_evaluate_info *info) /* Create and initialize a new walk state */ - info->pass_number = 3; + info->pass_number = ACPI_IMODE_EXECUTE; walk_state = acpi_ds_create_walk_state(info->obj_desc->method.owner_id, NULL, NULL, NULL); diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index 287da6f..7b28d93 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -162,7 +162,7 @@ struct acpi_mutex_info { typedef enum { ACPI_IMODE_LOAD_PASS1 = 0x01, ACPI_IMODE_LOAD_PASS2 = 0x02, - ACPI_IMODE_EXECUTE = 0x0E + ACPI_IMODE_EXECUTE = 0x03 } acpi_interpreter_mode; union acpi_name_union { -- cgit v0.10.2 From 3effba32069514e56bcb778f90cd34fdbac79a50 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Update comments Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/namespace/nswalk.c b/drivers/acpi/namespace/nswalk.c index a138fcb..c6619d8 100644 --- a/drivers/acpi/namespace/nswalk.c +++ b/drivers/acpi/namespace/nswalk.c @@ -193,21 +193,28 @@ acpi_ns_walk_namespace(acpi_object_type type, acpi_ns_get_next_node(ACPI_TYPE_ANY, parent_node, child_node); if (child_node) { - /* - * Found node, Get the type if we are not - * searching for ANY - */ + + /* Found node, Get the type if we are not searching for ANY */ + if (type != ACPI_TYPE_ANY) { child_type = child_node->type; } + /* + * 1) Type must match + * 2) Permanent namespace nodes are OK + * 3) Ignore temporary nodes unless told otherwise. Typically, + * the temporary nodes can cause a race condition where they can + * be deleted during the execution of the user function. Only the + * debugger namespace dump will examine the temporary nodes. + */ if ((child_type == type) && (!(child_node->flags & ANOBJ_TEMPORARY) || (child_node->flags & ANOBJ_TEMPORARY) && (flags & ACPI_NS_WALK_TEMP_NODES))) { /* - * Found a matching node, invoke the user - * callback function + * Found a matching node, invoke the user callback function. + * Unlock the namespace if flag is set. */ if (flags & ACPI_NS_WALK_UNLOCK) { mutex_status = @@ -219,8 +226,9 @@ acpi_ns_walk_namespace(acpi_object_type type, } } - status = user_function(child_node, level, - context, return_value); + status = + user_function(child_node, level, context, + return_value); if (flags & ACPI_NS_WALK_UNLOCK) { mutex_status = @@ -254,20 +262,17 @@ acpi_ns_walk_namespace(acpi_object_type type, } /* - * Depth first search: - * Attempt to go down another level in the namespace - * if we are allowed to. Don't go any further if we - * have reached the caller specified maximum depth - * or if the user function has specified that the - * maximum depth has been reached. + * Depth first search: Attempt to go down another level in the + * namespace if we are allowed to. Don't go any further if we have + * reached the caller specified maximum depth or if the user + * function has specified that the maximum depth has been reached. */ if ((level < max_depth) && (status != AE_CTRL_DEPTH)) { if (acpi_ns_get_next_node (ACPI_TYPE_ANY, child_node, NULL)) { - /* - * There is at least one child of this - * node, visit the onde - */ + + /* There is at least one child of this node, visit it */ + level++; parent_node = child_node; child_node = NULL; @@ -275,9 +280,8 @@ acpi_ns_walk_namespace(acpi_object_type type, } } else { /* - * No more children of this node (acpi_ns_get_next_node - * failed), go back upwards in the namespace tree to - * the node's parent. + * No more children of this node (acpi_ns_get_next_node failed), go + * back upwards in the namespace tree to the node's parent. */ level--; child_node = parent_node; -- cgit v0.10.2 From c1014629c0fc563be65e675e72bcc9bd7db50195 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:21 +0300 Subject: ACPICA: Abort downward walk on temporary node detection. Enhancement to code that ignores temporary namespace nodes Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/namespace/nswalk.c b/drivers/acpi/namespace/nswalk.c index c6619d8..bccf27d 100644 --- a/drivers/acpi/namespace/nswalk.c +++ b/drivers/acpi/namespace/nswalk.c @@ -194,24 +194,28 @@ acpi_ns_walk_namespace(acpi_object_type type, child_node); if (child_node) { - /* Found node, Get the type if we are not searching for ANY */ + /* Found next child, get the type if we are not searching for ANY */ if (type != ACPI_TYPE_ANY) { child_type = child_node->type; } /* - * 1) Type must match - * 2) Permanent namespace nodes are OK - * 3) Ignore temporary nodes unless told otherwise. Typically, - * the temporary nodes can cause a race condition where they can - * be deleted during the execution of the user function. Only the - * debugger namespace dump will examine the temporary nodes. + * Ignore all temporary namespace nodes (created during control + * method execution) unless told otherwise. These temporary nodes + * can cause a race condition because they can be deleted during the + * execution of the user function (if the namespace is unlocked before + * invocation of the user function.) Only the debugger namespace dump + * will examine the temporary nodes. */ - if ((child_type == type) && - (!(child_node->flags & ANOBJ_TEMPORARY) || - (child_node->flags & ANOBJ_TEMPORARY) - && (flags & ACPI_NS_WALK_TEMP_NODES))) { + if ((child_node->flags & ANOBJ_TEMPORARY) && + !(flags & ACPI_NS_WALK_TEMP_NODES)) { + status = AE_CTRL_DEPTH; + } + + /* Type must match requested type */ + + else if (child_type == type) { /* * Found a matching node, invoke the user callback function. * Unlock the namespace if flag is set. -- cgit v0.10.2 From f1c2b1daf040d2feebfbbd4a0cd80cde856fc031 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Fixes for parameter validation. Extra checks for valid handle/path combinations, BZ 478 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/namespace/nsxfname.c b/drivers/acpi/namespace/nsxfname.c index 978213a..408bd11 100644 --- a/drivers/acpi/namespace/nsxfname.c +++ b/drivers/acpi/namespace/nsxfname.c @@ -84,38 +84,41 @@ acpi_get_handle(acpi_handle parent, /* Convert a parent handle to a prefix node */ if (parent) { - status = acpi_ut_acquire_mutex(ACPI_MTX_NAMESPACE); - if (ACPI_FAILURE(status)) { - return (status); - } - prefix_node = acpi_ns_map_handle_to_node(parent); if (!prefix_node) { - (void)acpi_ut_release_mutex(ACPI_MTX_NAMESPACE); return (AE_BAD_PARAMETER); } + } + + /* + * Valid cases are: + * 1) Fully qualified pathname + * 2) Parent + Relative pathname + * + * Error for + */ + if (acpi_ns_valid_root_prefix(pathname[0])) { - status = acpi_ut_release_mutex(ACPI_MTX_NAMESPACE); - if (ACPI_FAILURE(status)) { - return (status); + /* Pathname is fully qualified (starts with '\') */ + + /* Special case for root-only, since we can't search for it */ + + if (!ACPI_STRCMP(pathname, ACPI_NS_ROOT_PATH)) { + *ret_handle = + acpi_ns_convert_entry_to_handle(acpi_gbl_root_node); + return (AE_OK); } - } + } else if (!prefix_node) { - /* Special case for root, since we can't search for it */ + /* Relative path with null prefix is disallowed */ - if (ACPI_STRCMP(pathname, ACPI_NS_ROOT_PATH) == 0) { - *ret_handle = - acpi_ns_convert_entry_to_handle(acpi_gbl_root_node); - return (AE_OK); + return (AE_BAD_PARAMETER); } - /* - * Find the Node and convert to a handle - */ - status = acpi_ns_get_node(prefix_node, pathname, ACPI_NS_NO_UPSEARCH, - &node); + /* Find the Node and convert to a handle */ - *ret_handle = NULL; + status = + acpi_ns_get_node(prefix_node, pathname, ACPI_NS_NO_UPSEARCH, &node); if (ACPI_SUCCESS(status)) { *ret_handle = acpi_ns_convert_entry_to_handle(node); } -- cgit v0.10.2 From a7a22fa9c368ba22f13b87585052b8cdbbc18f7a Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Update version to 20061011 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index bd5560b..9aa3b19 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20060927 +#define ACPI_CA_VERSION 0x20061011 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, -- cgit v0.10.2 From ceb6c46839021d5c7c338d48deac616944660124 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Remove duplicate table manager Signed-off-by: Len Brown diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index 9adabc4..543eac5 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -169,16 +169,16 @@ char *__acpi_map_table(unsigned long phys, unsigned long size) struct acpi_table_mcfg_config *pci_mmcfg_config; int pci_mmcfg_config_num; -int __init acpi_parse_mcfg(unsigned long phys_addr, unsigned long size) +int __init acpi_parse_mcfg(struct acpi_table_header *header) { struct acpi_table_mcfg *mcfg; unsigned long i; int config_size; - if (!phys_addr || !size) + if (!header) return -EINVAL; - mcfg = (struct acpi_table_mcfg *)__acpi_map_table(phys_addr, size); + mcfg = (struct acpi_table_mcfg *)header; if (!mcfg) { printk(KERN_WARNING PREFIX "Unable to map MCFG\n"); return -ENODEV; @@ -186,7 +186,7 @@ int __init acpi_parse_mcfg(unsigned long phys_addr, unsigned long size) /* how many config structures do we have */ pci_mmcfg_config_num = 0; - i = size - sizeof(struct acpi_table_mcfg); + i = header->length - sizeof(struct acpi_table_mcfg); while (i >= sizeof(struct acpi_table_mcfg_config)) { ++pci_mmcfg_config_num; i -= sizeof(struct acpi_table_mcfg_config); @@ -220,14 +220,14 @@ int __init acpi_parse_mcfg(unsigned long phys_addr, unsigned long size) #endif /* CONFIG_PCI_MMCONFIG */ #ifdef CONFIG_X86_LOCAL_APIC -static int __init acpi_parse_madt(unsigned long phys_addr, unsigned long size) +static int __init acpi_parse_madt(struct acpi_table_header *header) { struct acpi_table_madt *madt = NULL; - if (!phys_addr || !size || !cpu_has_apic) + if (!header|| !cpu_has_apic) return -EINVAL; - madt = (struct acpi_table_madt *)__acpi_map_table(phys_addr, size); + madt = (struct acpi_table_madt *)header; if (!madt) { printk(KERN_WARNING PREFIX "Unable to map MADT\n"); return -ENODEV; @@ -619,14 +619,14 @@ acpi_scan_rsdp(unsigned long start, unsigned long length) return 0; } -static int __init acpi_parse_sbf(unsigned long phys_addr, unsigned long size) +static int __init acpi_parse_sbf(struct acpi_table_header *header) { struct acpi_table_sbf *sb; - if (!phys_addr || !size) + if (!header) return -EINVAL; - sb = (struct acpi_table_sbf *)__acpi_map_table(phys_addr, size); + sb = (struct acpi_table_sbf *)header; if (!sb) { printk(KERN_WARNING PREFIX "Unable to map SBF\n"); return -ENODEV; @@ -639,16 +639,16 @@ static int __init acpi_parse_sbf(unsigned long phys_addr, unsigned long size) #ifdef CONFIG_HPET_TIMER -static int __init acpi_parse_hpet(unsigned long phys, unsigned long size) +static int __init acpi_parse_hpet(struct acpi_table_header *header) { struct acpi_table_hpet *hpet_tbl; struct resource *hpet_res; resource_size_t res_start; - if (!phys || !size) + if (!header) return -EINVAL; - hpet_tbl = (struct acpi_table_hpet *)__acpi_map_table(phys, size); + hpet_tbl = (struct acpi_table_hpet *)header; if (!hpet_tbl) { printk(KERN_WARNING PREFIX "Unable to map HPET\n"); return -ENODEV; @@ -707,11 +707,11 @@ static int __init acpi_parse_hpet(unsigned long phys, unsigned long size) extern u32 pmtmr_ioport; #endif -static int __init acpi_parse_fadt(unsigned long phys, unsigned long size) +static int __init acpi_parse_fadt(struct acpi_table_header *header) { struct fadt_descriptor *fadt = NULL; - fadt = (struct fadt_descriptor *)__acpi_map_table(phys, size); + fadt = (struct fadt_descriptor *)header; if (!fadt) { printk(KERN_WARNING PREFIX "Unable to map FADT\n"); return 0; @@ -901,7 +901,7 @@ static void __init acpi_process_madt(void) #ifdef CONFIG_X86_LOCAL_APIC int count, error; - count = acpi_table_parse(ACPI_APIC, acpi_parse_madt); + count = acpi_table_parse("APIC", acpi_parse_madt); if (count >= 1) { /* @@ -1197,7 +1197,7 @@ int __init acpi_boot_table_init(void) return error; } - acpi_table_parse(ACPI_BOOT, acpi_parse_sbf); + acpi_table_parse("BOOT", acpi_parse_sbf); /* * blacklist may disable ACPI entirely @@ -1225,19 +1225,19 @@ int __init acpi_boot_init(void) if (acpi_disabled && !acpi_ht) return 1; - acpi_table_parse(ACPI_BOOT, acpi_parse_sbf); + acpi_table_parse("BOOT", acpi_parse_sbf); /* * set sci_int and PM timer address */ - acpi_table_parse(ACPI_FADT, acpi_parse_fadt); + acpi_table_parse(ACPI_SIG_FADT, acpi_parse_fadt); /* * Process the Multiple APIC Description Table (MADT), if present */ acpi_process_madt(); - acpi_table_parse(ACPI_HPET, acpi_parse_hpet); + acpi_table_parse("HPET", acpi_parse_hpet); return 0; } diff --git a/arch/i386/kernel/acpi/earlyquirk.c b/arch/i386/kernel/acpi/earlyquirk.c index 4b60af7..4261c85 100644 --- a/arch/i386/kernel/acpi/earlyquirk.c +++ b/arch/i386/kernel/acpi/earlyquirk.c @@ -16,7 +16,7 @@ static int nvidia_hpet_detected __initdata; -static int __init nvidia_hpet_check(unsigned long phys, unsigned long size) +static int __init nvidia_hpet_check(struct acpi_table_header *header) { nvidia_hpet_detected = 1; return 0; @@ -30,7 +30,7 @@ static int __init check_bridge(int vendor, int device) is enabled. */ if (!acpi_use_timer_override && vendor == PCI_VENDOR_ID_NVIDIA) { nvidia_hpet_detected = 0; - acpi_table_parse(ACPI_HPET, nvidia_hpet_check); + acpi_table_parse("HPET", nvidia_hpet_check); if (nvidia_hpet_detected == 0) { acpi_skip_timer_override = 1; printk(KERN_INFO "Nvidia board " diff --git a/arch/i386/mach-es7000/es7000.h b/arch/i386/mach-es7000/es7000.h index 80566ca..c8d5aa1 100644 --- a/arch/i386/mach-es7000/es7000.h +++ b/arch/i386/mach-es7000/es7000.h @@ -84,15 +84,6 @@ struct es7000_oem_table { }; #ifdef CONFIG_ACPI -struct acpi_table_sdt { - unsigned long pa; - unsigned long count; - struct { - unsigned long pa; - enum acpi_table_id id; - unsigned long size; - } entry[50]; -}; struct oem_table { struct acpi_table_header Header; diff --git a/arch/i386/mach-es7000/es7000plat.c b/arch/i386/mach-es7000/es7000plat.c index 3d0fc853..9be6cea 100644 --- a/arch/i386/mach-es7000/es7000plat.c +++ b/arch/i386/mach-es7000/es7000plat.c @@ -160,51 +160,14 @@ parse_unisys_oem (char *oemptr) int __init find_unisys_acpi_oem_table(unsigned long *oem_addr) { - struct acpi_table_rsdp *rsdp = NULL; - unsigned long rsdp_phys = 0; - struct acpi_table_header *header = NULL; - int i; - struct acpi_table_sdt sdt; - - rsdp_phys = acpi_find_rsdp(); - rsdp = __va(rsdp_phys); - if (rsdp->rsdt_address) { - struct acpi_table_rsdt *mapped_rsdt = NULL; - sdt.pa = rsdp->rsdt_address; - - header = (struct acpi_table_header *) - __acpi_map_table(sdt.pa, sizeof(struct acpi_table_header)); - if (!header) - return -ENODEV; - - sdt.count = (header->length - sizeof(struct acpi_table_header)) >> 3; - mapped_rsdt = (struct acpi_table_rsdt *) - __acpi_map_table(sdt.pa, header->length); - if (!mapped_rsdt) - return -ENODEV; - - header = &mapped_rsdt->header; - - for (i = 0; i < sdt.count; i++) - sdt.entry[i].pa = (unsigned long) mapped_rsdt->entry[i]; - }; - for (i = 0; i < sdt.count; i++) { - - header = (struct acpi_table_header *) - __acpi_map_table(sdt.entry[i].pa, - sizeof(struct acpi_table_header)); - if (!header) - continue; - if (!strncmp((char *) &header->signature, "OEM1", 4)) { - if (!strncmp((char *) &header->oem_id, "UNISYS", 6)) { - void *addr; - struct oem_table *t; - acpi_table_print(header, sdt.entry[i].pa); - t = (struct oem_table *) __acpi_map_table(sdt.entry[i].pa, header->length); - addr = (void *) __acpi_map_table(t->OEMTableAddr, t->OEMTableSize); - *oem_addr = (unsigned long) addr; - return 0; - } + struct acpi_table_header *header = NULL; + int i = 0; + while (ACPI_SUCCESS(acpi_get_table("OEM1", i++, &header))) { + if (!memcmp((char *) &header->oem_id, "UNISYS", 6)) { + struct oem_table *t = (struct oem_table *)header; + *oem_addr = (unsigned long)__acpi_map_table(t->OEMTableAddr, + t->OEMTableSize); + return 0; } } return -1; diff --git a/arch/i386/pci/mmconfig.c b/arch/i386/pci/mmconfig.c index e2616a2..80522e3 100644 --- a/arch/i386/pci/mmconfig.c +++ b/arch/i386/pci/mmconfig.c @@ -199,7 +199,7 @@ void __init pci_mmcfg_init(int type) if ((pci_probe & PCI_PROBE_MMCONF) == 0) return; - acpi_table_parse(ACPI_MCFG, acpi_parse_mcfg); + acpi_table_parse("MCFG", acpi_parse_mcfg); if ((pci_mmcfg_config_num == 0) || (pci_mmcfg_config == NULL) || (pci_mmcfg_config[0].base_address == 0)) diff --git a/drivers/acpi/tables.c b/drivers/acpi/tables.c index 5bb1431..962ff29 100644 --- a/drivers/acpi/tables.c +++ b/drivers/acpi/tables.c @@ -38,71 +38,11 @@ #define ACPI_MAX_TABLES 128 -static char *acpi_table_signatures[ACPI_TABLE_COUNT] = { - [ACPI_TABLE_UNKNOWN] = "????", - [ACPI_APIC] = "APIC", - [ACPI_BOOT] = "BOOT", - [ACPI_DBGP] = "DBGP", - [ACPI_DSDT] = "DSDT", - [ACPI_ECDT] = "ECDT", - [ACPI_ETDT] = "ETDT", - [ACPI_FADT] = "FACP", - [ACPI_FACS] = "FACS", - [ACPI_OEMX] = "OEM", - [ACPI_PSDT] = "PSDT", - [ACPI_SBST] = "SBST", - [ACPI_SLIT] = "SLIT", - [ACPI_SPCR] = "SPCR", - [ACPI_SRAT] = "SRAT", - [ACPI_SSDT] = "SSDT", - [ACPI_SPMI] = "SPMI", - [ACPI_HPET] = "HPET", - [ACPI_MCFG] = "MCFG", -}; - static char *mps_inti_flags_polarity[] = { "dfl", "high", "res", "low" }; static char *mps_inti_flags_trigger[] = { "dfl", "edge", "res", "level" }; -/* System Description Table (RSDT/XSDT) */ -struct acpi_table_sdt { - unsigned long pa; - enum acpi_table_id id; - unsigned long size; -} __attribute__ ((packed)); - -static unsigned long sdt_pa; /* Physical Address */ -static unsigned long sdt_count; /* Table count */ - -static struct acpi_table_sdt sdt_entry[ACPI_MAX_TABLES] __initdata; static struct acpi_table_desc initial_tables[ACPI_MAX_TABLES] __initdata; -void acpi_table_print(struct acpi_table_header *header, unsigned long phys_addr) -{ - char *name = NULL; - - if (!header) - return; - - /* Some table signatures aren't good table names */ - - if (!strncmp((char *)&header->signature, - acpi_table_signatures[ACPI_APIC], - sizeof(header->signature))) { - name = "MADT"; - } else if (!strncmp((char *)&header->signature, - acpi_table_signatures[ACPI_FADT], - sizeof(header->signature))) { - name = "FADT"; - } else - name = header->signature; - - printk(KERN_DEBUG PREFIX - "%.4s (v%3.3d %6.6s %8.8s 0x%08x %.4s 0x%08x) @ 0x%p\n", name, - header->revision, header->oem_id, header->oem_table_id, - header->oem_revision, header->asl_compiler_id, - header->asl_compiler_revision, (void *)phys_addr); -} - void acpi_table_print_madt_entry(acpi_table_entry_header * header) { if (!header) @@ -226,123 +166,32 @@ void acpi_table_print_madt_entry(acpi_table_entry_header * header) } } -static int -acpi_table_compute_checksum(void *table_pointer, unsigned long length) -{ - u8 *p = table_pointer; - unsigned long remains = length; - unsigned long sum = 0; - - if (!p || !length) - return -EINVAL; - - while (remains--) - sum += *p++; - - return (sum & 0xFF); -} - -/* - * acpi_get_table_header_early() - * for acpi_blacklisted(), acpi_table_get_sdt() - */ -int __init -acpi_get_table_header_early(enum acpi_table_id id, - struct acpi_table_header **header) -{ - unsigned int i; - enum acpi_table_id temp_id; - - /* DSDT is different from the rest */ - if (id == ACPI_DSDT) - temp_id = ACPI_FADT; - else - temp_id = id; - - /* Locate the table. */ - - for (i = 0; i < sdt_count; i++) { - if (sdt_entry[i].id != temp_id) - continue; - *header = (void *) - __acpi_map_table(sdt_entry[i].pa, sdt_entry[i].size); - if (!*header) { - printk(KERN_WARNING PREFIX "Unable to map %s\n", - acpi_table_signatures[temp_id]); - return -ENODEV; - } - break; - } - - if (!*header) { - printk(KERN_WARNING PREFIX "%s not present\n", - acpi_table_signatures[id]); - return -ENODEV; - } - - /* Map the DSDT header via the pointer in the FADT */ - if (id == ACPI_DSDT) { - struct fadt_descriptor *fadt = - (struct fadt_descriptor *)*header; - - if (fadt->header.revision == 3 && fadt->Xdsdt) { - *header = (void *)__acpi_map_table(fadt->Xdsdt, - sizeof(struct - acpi_table_header)); - } else if (fadt->dsdt) { - *header = (void *)__acpi_map_table(fadt->dsdt, - sizeof(struct - acpi_table_header)); - } else - *header = NULL; - - if (!*header) { - printk(KERN_WARNING PREFIX "Unable to map DSDT\n"); - return -ENODEV; - } - } - - return 0; -} int __init -acpi_table_parse_madt_family(enum acpi_table_id id, +acpi_table_parse_madt_family(char *id, unsigned long madt_size, int entry_id, acpi_madt_entry_handler handler, unsigned int max_entries) { - void *madt = NULL; + struct acpi_table_header *madt = NULL; acpi_table_entry_header *entry; unsigned int count = 0; unsigned long madt_end; - unsigned int i; if (!handler) return -EINVAL; /* Locate the MADT (if exists). There should only be one. */ - for (i = 0; i < sdt_count; i++) { - if (sdt_entry[i].id != id) - continue; - madt = (void *) - __acpi_map_table(sdt_entry[i].pa, sdt_entry[i].size); - if (!madt) { - printk(KERN_WARNING PREFIX "Unable to map %s\n", - acpi_table_signatures[id]); - return -ENODEV; - } - break; - } + acpi_get_table(id, 0, &madt); if (!madt) { - printk(KERN_WARNING PREFIX "%s not present\n", - acpi_table_signatures[id]); + printk(KERN_WARNING PREFIX "%4.4s not present\n", id); return -ENODEV; } - madt_end = (unsigned long)madt + sdt_entry[i].size; + madt_end = (unsigned long)madt + madt->length; /* Parse all entries looking for a match. */ @@ -360,9 +209,8 @@ acpi_table_parse_madt_family(enum acpi_table_id id, ((unsigned long)entry + entry->length); } if (max_entries && count > max_entries) { - printk(KERN_WARNING PREFIX "[%s:0x%02x] ignored %i entries of " - "%i found\n", acpi_table_signatures[id], entry_id, - count - max_entries, count); + printk(KERN_WARNING PREFIX "[%4.4s:0x%02x] ignored %i entries of " + "%i found\n", id, entry_id, count - max_entries, count); } return count; @@ -372,195 +220,24 @@ int __init acpi_table_parse_madt(enum acpi_madt_entry_id id, acpi_madt_entry_handler handler, unsigned int max_entries) { - return acpi_table_parse_madt_family(ACPI_APIC, + return acpi_table_parse_madt_family("APIC", sizeof(struct acpi_table_madt), id, handler, max_entries); } -int __init acpi_table_parse(enum acpi_table_id id, acpi_table_handler handler) +int __init acpi_table_parse(char *id, acpi_table_handler handler) { - int count = 0; - unsigned int i = 0; + struct acpi_table_header *table = NULL; if (!handler) return -EINVAL; - for (i = 0; i < sdt_count; i++) { - if (sdt_entry[i].id != id) - continue; - count++; - if (count == 1) - handler(sdt_entry[i].pa, sdt_entry[i].size); - - else - printk(KERN_WARNING PREFIX - "%d duplicate %s table ignored.\n", count, - acpi_table_signatures[id]); - } - - return count; -} - -static int __init acpi_table_get_sdt(struct acpi_table_rsdp *rsdp) -{ - struct acpi_table_header *header = NULL; - unsigned int i, id = 0; - - if (!rsdp) - return -EINVAL; - - /* First check XSDT (but only on ACPI 2.0-compatible systems) */ - - if ((rsdp->revision >= 2) && rsdp->xsdt_physical_address) { - - struct acpi_table_xsdt *mapped_xsdt = NULL; - - sdt_pa = rsdp->xsdt_physical_address; - - /* map in just the header */ - header = (struct acpi_table_header *) - __acpi_map_table(sdt_pa, sizeof(struct acpi_table_header)); - - if (!header) { - printk(KERN_WARNING PREFIX - "Unable to map XSDT header\n"); - return -ENODEV; - } - - /* remap in the entire table before processing */ - mapped_xsdt = (struct acpi_table_xsdt *) - __acpi_map_table(sdt_pa, header->length); - if (!mapped_xsdt) { - printk(KERN_WARNING PREFIX "Unable to map XSDT\n"); - return -ENODEV; - } - header = &mapped_xsdt->header; - - if (strncmp(header->signature, "XSDT", 4)) { - printk(KERN_WARNING PREFIX - "XSDT signature incorrect\n"); - return -ENODEV; - } - - if (acpi_table_compute_checksum(header, header->length)) { - printk(KERN_WARNING PREFIX "Invalid XSDT checksum\n"); - return -ENODEV; - } - - sdt_count = - (header->length - sizeof(struct acpi_table_header)) >> 3; - if (sdt_count > ACPI_MAX_TABLES) { - printk(KERN_WARNING PREFIX - "Truncated %lu XSDT entries\n", - (sdt_count - ACPI_MAX_TABLES)); - sdt_count = ACPI_MAX_TABLES; - } - - for (i = 0; i < sdt_count; i++) - sdt_entry[i].pa = (unsigned long)mapped_xsdt->table_offset_entry[i]; - } - - /* Then check RSDT */ - - else if (rsdp->rsdt_physical_address) { - - struct acpi_table_rsdt *mapped_rsdt = NULL; - - sdt_pa = rsdp->rsdt_physical_address; - - /* map in just the header */ - header = (struct acpi_table_header *) - __acpi_map_table(sdt_pa, sizeof(struct acpi_table_header)); - if (!header) { - printk(KERN_WARNING PREFIX - "Unable to map RSDT header\n"); - return -ENODEV; - } - - /* remap in the entire table before processing */ - mapped_rsdt = (struct acpi_table_rsdt *) - __acpi_map_table(sdt_pa, header->length); - if (!mapped_rsdt) { - printk(KERN_WARNING PREFIX "Unable to map RSDT\n"); - return -ENODEV; - } - header = &mapped_rsdt->header; - - if (strncmp(header->signature, "RSDT", 4)) { - printk(KERN_WARNING PREFIX - "RSDT signature incorrect\n"); - return -ENODEV; - } - - if (acpi_table_compute_checksum(header, header->length)) { - printk(KERN_WARNING PREFIX "Invalid RSDT checksum\n"); - return -ENODEV; - } - - sdt_count = - (header->length - sizeof(struct acpi_table_header)) >> 2; - if (sdt_count > ACPI_MAX_TABLES) { - printk(KERN_WARNING PREFIX - "Truncated %lu RSDT entries\n", - (sdt_count - ACPI_MAX_TABLES)); - sdt_count = ACPI_MAX_TABLES; - } - - for (i = 0; i < sdt_count; i++) - sdt_entry[i].pa = (unsigned long)mapped_rsdt->table_offset_entry[i]; - } - - else { - printk(KERN_WARNING PREFIX - "No System Description Table (RSDT/XSDT) specified in RSDP\n"); - return -ENODEV; - } - - acpi_table_print(header, sdt_pa); - - for (i = 0; i < sdt_count; i++) { - - /* map in just the header */ - header = (struct acpi_table_header *) - __acpi_map_table(sdt_entry[i].pa, - sizeof(struct acpi_table_header)); - if (!header) - continue; - - /* remap in the entire table before processing */ - header = (struct acpi_table_header *) - __acpi_map_table(sdt_entry[i].pa, header->length); - if (!header) - continue; - - acpi_table_print(header, sdt_entry[i].pa); - - if (acpi_table_compute_checksum(header, header->length)) { - printk(KERN_WARNING " >>> ERROR: Invalid checksum\n"); - continue; - } - - sdt_entry[i].size = header->length; - - for (id = 0; id < ACPI_TABLE_COUNT; id++) { - if (!strncmp((char *)&header->signature, - acpi_table_signatures[id], - sizeof(header->signature))) { - sdt_entry[i].id = id; - } - } - } - - /* - * The DSDT is *not* in the RSDT (why not? no idea.) but we want - * to print its info, because this is what people usually blacklist - * against. Unfortunately, we don't know the phys_addr, so just - * print 0. Maybe no one will notice. - */ - if (!acpi_get_table_header_early(ACPI_DSDT, &header)) - acpi_table_print(header, 0); - - return 0; + acpi_get_table(id, 0, &table); + if (table) { + handler(table); + return 1; + } else + return 0; } /* @@ -574,47 +251,6 @@ static int __init acpi_table_get_sdt(struct acpi_table_rsdp *rsdp) int __init acpi_table_init(void) { - struct acpi_table_rsdp *rsdp = NULL; - unsigned long rsdp_phys = 0; - int result = 0; - - /* Locate and map the Root System Description Table (RSDP) */ - - rsdp_phys = acpi_find_rsdp(); - if (!rsdp_phys) { - printk(KERN_ERR PREFIX "Unable to locate RSDP\n"); - return -ENODEV; - } - - rsdp = (struct acpi_table_rsdp *)__acpi_map_table(rsdp_phys, - sizeof(struct acpi_table_rsdp)); - if (!rsdp) { - printk(KERN_WARNING PREFIX "Unable to map RSDP\n"); - return -ENODEV; - } - - printk(KERN_DEBUG PREFIX - "RSDP (v%3.3d %6.6s ) @ 0x%p\n", - rsdp->revision, rsdp->oem_id, (void *)rsdp_phys); - - if (rsdp->revision < 2) - result = - acpi_table_compute_checksum(rsdp, ACPI_RSDP_REV0_SIZE); - else - result = - acpi_table_compute_checksum(rsdp, rsdp->length); - - if (result) { - printk(KERN_WARNING " >>> ERROR: Invalid checksum\n"); - return -ENODEV; - } - - /* Locate and map the System Description table (RSDT/XSDT) */ - - if (acpi_table_get_sdt(rsdp)) - return -ENODEV; - acpi_initialize_tables(initial_tables, ACPI_MAX_TABLES, 0); - return 0; } diff --git a/include/linux/acpi.h b/include/linux/acpi.h index b3e8a26..88cb1fe 100644 --- a/include/linux/acpi.h +++ b/include/linux/acpi.h @@ -340,7 +340,7 @@ enum acpi_table_id { ACPI_TABLE_COUNT }; -typedef int (*acpi_table_handler) (unsigned long phys_addr, unsigned long size); +typedef int (*acpi_table_handler) (struct acpi_table_header *header); extern acpi_table_handler acpi_table_ops[ACPI_TABLE_COUNT]; @@ -353,11 +353,10 @@ int acpi_boot_table_init (void); int acpi_numa_init (void); int acpi_table_init (void); -int acpi_table_parse (enum acpi_table_id id, acpi_table_handler handler); -int acpi_get_table_header_early (enum acpi_table_id id, struct acpi_table_header **header); +int acpi_table_parse (char *id, acpi_table_handler handler); int acpi_table_parse_madt (enum acpi_madt_entry_id id, acpi_madt_entry_handler handler, unsigned int max_entries); int acpi_table_parse_srat (enum acpi_srat_entry_id id, acpi_madt_entry_handler handler, unsigned int max_entries); -int acpi_parse_mcfg (unsigned long phys_addr, unsigned long size); +int acpi_parse_mcfg (struct acpi_table_header *header); void acpi_table_print (struct acpi_table_header *header, unsigned long phys_addr); void acpi_table_print_madt_entry (acpi_table_entry_header *madt); void acpi_table_print_srat_entry (acpi_table_entry_header *srat); -- cgit v0.10.2 From cee324b145a1e5488b34191de670e5ed1d346ebb Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: use new ACPI headers. Signed-off-by: Len Brown diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index 543eac5..cbbcf9c 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -357,7 +357,7 @@ static void __init acpi_sci_ioapic_setup(u32 gsi, u16 polarity, u16 trigger) /* * stash over-ride to indicate we've been here - * and for later update of acpi_fadt + * and for later update of acpi_gbl_FADT */ acpi_sci_override_gsi = gsi; return; @@ -376,7 +376,7 @@ acpi_parse_int_src_ovr(acpi_table_entry_header * header, acpi_table_print_madt_entry(header); - if (intsrc->bus_irq == acpi_fadt.sci_int) { + if (intsrc->bus_irq == acpi_gbl_FADT.sci_interrupt) { acpi_sci_ioapic_setup(intsrc->global_irq, intsrc->flags.polarity, intsrc->flags.trigger); @@ -709,9 +709,9 @@ extern u32 pmtmr_ioport; static int __init acpi_parse_fadt(struct acpi_table_header *header) { - struct fadt_descriptor *fadt = NULL; + struct acpi_table_fadt *fadt = NULL; - fadt = (struct fadt_descriptor *)header; + fadt = (struct acpi_table_fadt *)header; if (!fadt) { printk(KERN_WARNING PREFIX "Unable to map FADT\n"); return 0; @@ -873,7 +873,7 @@ static int __init acpi_parse_madt_ioapic_entries(void) * pretend we got one so we can set the SCI flags. */ if (!acpi_sci_override_gsi) - acpi_sci_ioapic_setup(acpi_fadt.sci_int, 0, 0); + acpi_sci_ioapic_setup(acpi_gbl_FADT.sci_interrupt, 0, 0); /* Fill in identity legacy mapings where no override */ mp_config_acpi_legacy_irqs(); diff --git a/arch/i386/kernel/cpu/cpufreq/longhaul.c b/arch/i386/kernel/cpu/cpufreq/longhaul.c index e940e00..a3db933 100644 --- a/arch/i386/kernel/cpu/cpufreq/longhaul.c +++ b/arch/i386/kernel/cpu/cpufreq/longhaul.c @@ -190,7 +190,7 @@ static void do_powersaver(int cx_address, unsigned int clock_ratio_index) /* Invoke C3 */ inb(cx_address); /* Dummy op - must do something useless after P_LVL3 read */ - t = inl(acpi_fadt.xpm_tmr_blk.address); + t = inl(acpi_gbl_FADT.xpm_timer_block.address); } /* Disable bus ratio bit */ local_irq_disable(); @@ -250,8 +250,7 @@ static void longhaul_setstate(unsigned int clock_ratio_index) outb(3, 0x22); } else if ((pr != NULL) && pr->flags.bm_control) { /* Disable bus master arbitration */ - acpi_set_register(ACPI_BITREG_ARB_DISABLE, 1, - ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_ARB_DISABLE, 1); } switch (longhaul_version) { @@ -281,8 +280,7 @@ static void longhaul_setstate(unsigned int clock_ratio_index) case TYPE_POWERSAVER: if (longhaul_flags & USE_ACPI_C3) { /* Don't allow wakeup */ - acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, 0, - ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_BUS_MASTER_RLD, 0); do_powersaver(cx->address, clock_ratio_index); } else { do_powersaver(0, clock_ratio_index); @@ -295,8 +293,7 @@ static void longhaul_setstate(unsigned int clock_ratio_index) outb(0, 0x22); } else if ((pr != NULL) && pr->flags.bm_control) { /* Enable bus master arbitration */ - acpi_set_register(ACPI_BITREG_ARB_DISABLE, 0, - ACPI_MTX_DO_NOT_LOCK); + acpi_set_register(ACPI_BITREG_ARB_DISABLE, 0); } outb(pic2_mask,0xA1); /* restore mask */ outb(pic1_mask,0x21); @@ -414,7 +411,7 @@ static int __init longhaul_get_ranges(void) highest_speed = calc_speed(maxmult); lowest_speed = calc_speed(minmult); dprintk ("FSB:%dMHz Lowest speed: %s Highest speed:%s\n", fsb, - print_speed(lowest_speed/1000), + print_speed(lowest_speed/1000), print_speed(highest_speed/1000)); if (lowest_speed == highest_speed) { @@ -498,7 +495,7 @@ static void __init longhaul_setup_voltagescaling(void) maxvid.mV/1000, maxvid.mV%1000, minvid.mV/1000, minvid.mV%1000, numvscales); - + j = 0; while (longhaul_table[j].frequency != CPUFREQ_TABLE_END) { speed = longhaul_table[j].frequency; diff --git a/arch/i386/kernel/mpparse.c b/arch/i386/kernel/mpparse.c index 49bff35..4f5983c 100644 --- a/arch/i386/kernel/mpparse.c +++ b/arch/i386/kernel/mpparse.c @@ -1057,7 +1057,7 @@ int mp_register_gsi(u32 gsi, int triggering, int polarity) static int gsi_to_irq[MAX_GSI_NUM]; /* Don't set up the ACPI SCI because it's already set up */ - if (acpi_fadt.sci_int == gsi) + if (acpi_gbl_FADT.sci_interrupt == gsi) return gsi; ioapic = mp_find_ioapic(gsi); @@ -1114,7 +1114,7 @@ int mp_register_gsi(u32 gsi, int triggering, int polarity) /* * Don't assign IRQ used by ACPI SCI */ - if (gsi == acpi_fadt.sci_int) + if (gsi == acpi_gbl_FADT.sci_interrupt) gsi = pci_irq++; gsi_to_irq[irq] = gsi; } else { diff --git a/arch/ia64/kernel/acpi.c b/arch/ia64/kernel/acpi.c index aa6f967..d37fb8e 100644 --- a/arch/ia64/kernel/acpi.c +++ b/arch/ia64/kernel/acpi.c @@ -617,7 +617,7 @@ EXPORT_SYMBOL(acpi_unregister_gsi); static int __init acpi_parse_fadt(unsigned long phys_addr, unsigned long size) { struct acpi_table_header *fadt_header; - struct fadt_descriptor *fadt; + struct acpi_table_fadt *fadt; if (!phys_addr || !size) return -EINVAL; @@ -626,9 +626,9 @@ static int __init acpi_parse_fadt(unsigned long phys_addr, unsigned long size) if (fadt_header->revision != 3) return -ENODEV; /* Only deal with ACPI 2.0 FADT */ - fadt = (struct fadt_descriptor *)fadt_header; + fadt = (struct acpi_table_fadt *)fadt_header; - acpi_register_gsi(fadt->sci_int, ACPI_LEVEL_SENSITIVE, ACPI_ACTIVE_LOW); + acpi_register_gsi(fadt->sci_interrupt, ACPI_LEVEL_SENSITIVE, ACPI_ACTIVE_LOW); return 0; } diff --git a/arch/x86_64/kernel/genapic.c b/arch/x86_64/kernel/genapic.c index b007433..0b3603a 100644 --- a/arch/x86_64/kernel/genapic.c +++ b/arch/x86_64/kernel/genapic.c @@ -58,8 +58,8 @@ void __init clustered_apic_check(void) * Some x86_64 machines use physical APIC mode regardless of how many * procs/clusters are present (x86_64 ES7000 is an example). */ - if (acpi_fadt.revision > FADT2_REVISION_ID) - if (acpi_fadt.force_apic_physical_destination_mode) { + if (acpi_gbl_FADT.header.revision > FADT2_REVISION_ID) + if (acpi_gbl_FADT.flags & ACPI_FADT_APIC_PHYSICAL) { genapic = &apic_cluster; goto print; } diff --git a/arch/x86_64/kernel/mpparse.c b/arch/x86_64/kernel/mpparse.c index 0807256..50dd8be 100644 --- a/arch/x86_64/kernel/mpparse.c +++ b/arch/x86_64/kernel/mpparse.c @@ -798,7 +798,7 @@ int mp_register_gsi(u32 gsi, int triggering, int polarity) return gsi; /* Don't set up the ACPI SCI because it's already set up */ - if (acpi_fadt.sci_int == gsi) + if (acpi_gbl_FADT.sci_interrupt == gsi) return gsi; ioapic = mp_find_ioapic(gsi); diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c index cb807c4..324b099 100644 --- a/drivers/acpi/bus.c +++ b/drivers/acpi/bus.c @@ -627,15 +627,15 @@ void __init acpi_early_init(void) acpi_sci_flags.trigger = 3; /* Set PIC-mode SCI trigger type */ - acpi_pic_sci_set_trigger(acpi_fadt.sci_int, + acpi_pic_sci_set_trigger(acpi_gbl_FADT.sci_interrupt, acpi_sci_flags.trigger); } else { extern int acpi_sci_override_gsi; /* - * now that acpi_fadt is initialized, + * now that acpi_gbl_FADT is initialized, * update it with result from INT_SRC_OVR parsing */ - acpi_fadt.sci_int = acpi_sci_override_gsi; + acpi_gbl_FADT.sci_interrupt = acpi_sci_override_gsi; } #endif diff --git a/drivers/acpi/osl.c b/drivers/acpi/osl.c index c1c2100..a28f5b8 100644 --- a/drivers/acpi/osl.c +++ b/drivers/acpi/osl.c @@ -245,7 +245,7 @@ acpi_os_install_interrupt_handler(u32 gsi, acpi_osd_handler handler, * FADT. It may not be the same if an interrupt source override exists * for the SCI. */ - gsi = acpi_fadt.sci_int; + gsi = acpi_gbl_FADT.sci_interrupt; if (acpi_gsi_to_irq(gsi, &irq) < 0) { printk(KERN_ERR PREFIX "SCI (ACPI GSI %d) not registered\n", gsi); diff --git a/drivers/acpi/pci_link.c b/drivers/acpi/pci_link.c index 662e429..0f683c8 100644 --- a/drivers/acpi/pci_link.c +++ b/drivers/acpi/pci_link.c @@ -513,7 +513,7 @@ int __init acpi_irq_penalty_init(void) } } /* Add a penalty for the SCI */ - acpi_irq_penalty[acpi_fadt.sci_int] += PIRQ_PENALTY_PCI_USING; + acpi_irq_penalty[acpi_gbl_FADT.sci_interrupt] += PIRQ_PENALTY_PCI_USING; return 0; } diff --git a/drivers/acpi/processor_core.c b/drivers/acpi/processor_core.c index 4d552f7..1b6bc66 100644 --- a/drivers/acpi/processor_core.c +++ b/drivers/acpi/processor_core.c @@ -431,7 +431,7 @@ static int acpi_processor_get_info(struct acpi_processor *pr) * Check to see if we have bus mastering arbitration control. This * is required for proper C3 usage (to maintain cache coherency). */ - if (acpi_fadt.pm2_control_block && acpi_fadt.pm2_control_length) { + if (acpi_gbl_FADT.pm2_control_block && acpi_gbl_FADT.pm2_control_length) { pr->flags.bm_control = 1; ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Bus mastering arbitration control present\n")); @@ -490,8 +490,8 @@ static int acpi_processor_get_info(struct acpi_processor *pr) object.processor.pblk_length); else { pr->throttling.address = object.processor.pblk_address; - pr->throttling.duty_offset = acpi_fadt.duty_offset; - pr->throttling.duty_width = acpi_fadt.duty_width; + pr->throttling.duty_offset = acpi_gbl_FADT.duty_offset; + pr->throttling.duty_width = acpi_gbl_FADT.duty_width; pr->pblk = object.processor.pblk_address; diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c index db21dda..1d633f7 100644 --- a/drivers/acpi/processor_idle.c +++ b/drivers/acpi/processor_idle.c @@ -160,7 +160,7 @@ static inline u32 ticks_elapsed(u32 t1, u32 t2) { if (t2 >= t1) return (t2 - t1); - else if (!(acpi_fadt.flags & ACPI_FADT_32BIT_TIMER)) + else if (!(acpi_gbl_FADT.flags & ACPI_FADT_32BIT_TIMER)) return (((0x00FFFFFF - t1) + t2) & 0x00FFFFFF); else return ((0xFFFFFFFF - t1) + t2); @@ -234,7 +234,7 @@ static void acpi_cstate_enter(struct acpi_processor_cx *cstate) /* Dummy wait op - must do something useless after P_LVL2 read because chipsets cannot guarantee that STPCLK# signal gets asserted in time to freeze execution properly. */ - unused = inl(acpi_fadt.xpm_timer_block.address); + unused = inl(acpi_gbl_FADT.xpm_timer_block.address); } } @@ -334,7 +334,7 @@ static void acpi_processor_idle(void) * detection phase, to work cleanly with logical CPU hotplug. */ if ((cx->type != ACPI_STATE_C1) && (num_online_cpus() > 1) && - !pr->flags.has_cst && !(acpi_fadt.flags & ACPI_FADT_C2_MP_SUPPORTED)) + !pr->flags.has_cst && !(acpi_gbl_FADT.flags & ACPI_FADT_C2_MP_SUPPORTED)) cx = &pr->power.states[ACPI_STATE_C1]; #endif @@ -380,11 +380,11 @@ static void acpi_processor_idle(void) case ACPI_STATE_C2: /* Get start time (ticks) */ - t1 = inl(acpi_fadt.xpm_timer_block.address); + t1 = inl(acpi_gbl_FADT.xpm_timer_block.address); /* Invoke C2 */ acpi_cstate_enter(cx); /* Get end time (ticks) */ - t2 = inl(acpi_fadt.xpm_timer_block.address); + t2 = inl(acpi_gbl_FADT.xpm_timer_block.address); #ifdef CONFIG_GENERIC_TIME /* TSC halts in C2, so notify users */ @@ -415,11 +415,11 @@ static void acpi_processor_idle(void) } /* Get start time (ticks) */ - t1 = inl(acpi_fadt.xpm_timer_block.address); + t1 = inl(acpi_gbl_FADT.xpm_timer_block.address); /* Invoke C3 */ acpi_cstate_enter(cx); /* Get end time (ticks) */ - t2 = inl(acpi_fadt.xpm_timer_block.address); + t2 = inl(acpi_gbl_FADT.xpm_timer_block.address); if (pr->flags.bm_check) { /* Enable bus master arbitration */ atomic_dec(&c3_cpu_count); @@ -451,7 +451,7 @@ static void acpi_processor_idle(void) #ifdef CONFIG_HOTPLUG_CPU /* Don't do promotion/demotion */ if ((cx->type == ACPI_STATE_C1) && (num_online_cpus() > 1) && - !pr->flags.has_cst && !(acpi_fadt.flags & ACPI_FADT_C2_MP_SUPPORTED)) { + !pr->flags.has_cst && !(acpi_gbl_FADT.flags & ACPI_FADT_C2_MP_SUPPORTED)) { next_state = cx; goto end; } @@ -622,7 +622,7 @@ static int acpi_processor_get_power_info_fadt(struct acpi_processor *pr) * an SMP system. */ if ((num_online_cpus() > 1) && - !(acpi_fadt.flags & ACPI_FADT_C2_MP_SUPPORTED)) + !(acpi_gbl_FADT.flags & ACPI_FADT_C2_MP_SUPPORTED)) return -ENODEV; #endif @@ -631,8 +631,8 @@ static int acpi_processor_get_power_info_fadt(struct acpi_processor *pr) pr->power.states[ACPI_STATE_C3].address = pr->pblk + 5; /* determine latencies from FADT */ - pr->power.states[ACPI_STATE_C2].latency = acpi_fadt.C2latency; - pr->power.states[ACPI_STATE_C3].latency = acpi_fadt.C3latency; + pr->power.states[ACPI_STATE_C2].latency = acpi_gbl_FADT.C2latency; + pr->power.states[ACPI_STATE_C3].latency = acpi_gbl_FADT.C3latency; ACPI_DEBUG_PRINT((ACPI_DB_INFO, "lvl2[0x%08x] lvl3[0x%08x]\n", @@ -878,7 +878,7 @@ static void acpi_processor_power_verify_c3(struct acpi_processor *pr, * WBINVD should be set in fadt, for C3 state to be * supported on when bm_check is not required. */ - if (!(acpi_fadt.flags & ACPI_FADT_WBINVD)) { + if (!(acpi_gbl_FADT.flags & ACPI_FADT_WBINVD)) { ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Cache invalidation should work properly" " for C3 to be enabled on SMP systems\n")); @@ -1158,9 +1158,9 @@ int __cpuinit acpi_processor_power_init(struct acpi_processor *pr, if (!pr) return -EINVAL; - if (acpi_fadt.cst_control && !nocst) { + if (acpi_gbl_FADT.cst_control && !nocst) { status = - acpi_os_write_port(acpi_fadt.smi_command, acpi_fadt.cst_control, 8); + acpi_os_write_port(acpi_gbl_FADT.smi_command, acpi_gbl_FADT.cst_control, 8); if (ACPI_FAILURE(status)) { ACPI_EXCEPTION((AE_INFO, status, "Notifying BIOS of _CST ability failed")); diff --git a/drivers/acpi/processor_perflib.c b/drivers/acpi/processor_perflib.c index aabb988..058f13c 100644 --- a/drivers/acpi/processor_perflib.c +++ b/drivers/acpi/processor_perflib.c @@ -353,7 +353,7 @@ int acpi_processor_notify_smm(struct module *calling_module) is_done = -EIO; /* Can't write pstate_control to smi_command if either value is zero */ - if ((!acpi_fadt.smi_command) || (!acpi_fadt.pstate_control)) { + if ((!acpi_gbl_FADT.smi_command) || (!acpi_gbl_FADT.pstate_control)) { ACPI_DEBUG_PRINT((ACPI_DB_INFO, "No SMI port or pstate_control\n")); module_put(calling_module); return 0; @@ -361,15 +361,15 @@ int acpi_processor_notify_smm(struct module *calling_module) ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Writing pstate_control [0x%x] to smi_command [0x%x]\n", - acpi_fadt.pstate_control, acpi_fadt.smi_command)); + acpi_gbl_FADT.pstate_control, acpi_gbl_FADT.smi_command)); - status = acpi_os_write_port(acpi_fadt.smi_command, - (u32) acpi_fadt.pstate_control, 8); + status = acpi_os_write_port(acpi_gbl_FADT.smi_command, + (u32) acpi_gbl_FADT.pstate_control, 8); if (ACPI_FAILURE(status)) { ACPI_EXCEPTION((AE_INFO, status, "Failed to write pstate_control [0x%x] to " - "smi_command [0x%x]", acpi_fadt.pstate_control, - acpi_fadt.smi_command)); + "smi_command [0x%x]", acpi_gbl_FADT.pstate_control, + acpi_gbl_FADT.smi_command)); module_put(calling_module); return status; } diff --git a/drivers/acpi/processor_throttling.c b/drivers/acpi/processor_throttling.c index 0ec7dcd..89dff36 100644 --- a/drivers/acpi/processor_throttling.c +++ b/drivers/acpi/processor_throttling.c @@ -125,7 +125,7 @@ int acpi_processor_set_throttling(struct acpi_processor *pr, int state) /* Used to clear all duty_value bits */ duty_mask = pr->throttling.state_count - 1; - duty_mask <<= acpi_fadt.duty_offset; + duty_mask <<= acpi_gbl_FADT.duty_offset; duty_mask = ~duty_mask; } @@ -208,7 +208,7 @@ int acpi_processor_get_throttling_info(struct acpi_processor *pr) return 0; } - pr->throttling.state_count = 1 << acpi_fadt.duty_width; + pr->throttling.state_count = 1 << acpi_gbl_FADT.duty_width; /* * Compute state values. Note that throttling displays a linear power/ diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index b1692b1..0de4586 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -1333,7 +1333,7 @@ static int acpi_bus_scan_fixed(struct acpi_device *root) /* * Enumerate all fixed-feature devices. */ - if ((acpi_fadt.flags & ACPI_FADT_POWER_BUTTON) == 0) { + if ((acpi_gbl_FADT.flags & ACPI_FADT_POWER_BUTTON) == 0) { result = acpi_add_single_object(&device, acpi_root, NULL, ACPI_BUS_TYPE_POWER_BUTTON); @@ -1341,7 +1341,7 @@ static int acpi_bus_scan_fixed(struct acpi_device *root) result = acpi_start_single_object(device); } - if ((acpi_fadt.flags & ACPI_FADT_SLEEP_BUTTON) == 0) { + if ((acpi_gbl_FADT.flags & ACPI_FADT_SLEEP_BUTTON) == 0) { result = acpi_add_single_object(&device, acpi_root, NULL, ACPI_BUS_TYPE_SLEEP_BUTTON); diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index 8dab29a..d1a5363 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -144,7 +144,6 @@ ACPI_EXTERN u32 acpi_gbl_trace_flags; */ ACPI_EXTERN struct acpi_internal_rsdt acpi_gbl_root_table_list; ACPI_EXTERN struct acpi_table_fadt acpi_gbl_FADT; -#define acpi_fadt acpi_gbl_FADT extern acpi_native_uint acpi_gbl_permanent_mmap; /* These addresses are calculated from FADT address values */ diff --git a/include/acpi/actbl.h b/include/acpi/actbl.h index 6f63b3b..c5d5ec3 100644 --- a/include/acpi/actbl.h +++ b/include/acpi/actbl.h @@ -236,9 +236,6 @@ struct acpi_table_fadt { struct acpi_generic_address xgpe1_block; /* 64-bit Extended General Purpose Event 1 Reg Blk address */ }; -#define fadt_descriptor acpi_table_fadt -#define sci_int sci_interrupt - /* FADT flags */ #define ACPI_FADT_WBINVD (1) /* 00: The wbinvd instruction works properly */ diff --git a/include/acpi/actbl1.h b/include/acpi/actbl1.h index 3156d1a..b7178eb 100644 --- a/include/acpi/actbl1.h +++ b/include/acpi/actbl1.h @@ -669,16 +669,6 @@ struct acpi_srat_mem_affinity { #define ACPI_SRAT_MEM_HOT_PLUGGABLE (1<<1) /* 01: Memory region is hot pluggable */ #define ACPI_SRAT_MEM_NON_VOLATILE (1<<2) /* 02: Memory region is non-volatile */ -/* Memory types */ - -enum acpi_address_range_id { - ACPI_ADDRESS_RANGE_MEMORY = 1, - ACPI_ADDRESS_RANGE_RESERVED = 2, - ACPI_ADDRESS_RANGE_ACPI = 3, - ACPI_ADDRESS_RANGE_NVS = 4, - ACPI_ADDRESS_RANGE_COUNT = 5 -}; - /******************************************************************************* * * TCPA - Trusted Computing Platform Alliance table -- cgit v0.10.2 From ad363f80c386bc4701b1bc2cdf08ca9b96a9337b Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Remove duplicate table definitions. Signed-off-by: Len Brown diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index cbbcf9c..389a8a5 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -204,9 +204,9 @@ int __init acpi_parse_mcfg(struct acpi_table_header *header) return -ENOMEM; } - memcpy(pci_mmcfg_config, &mcfg->config, config_size); + memcpy(pci_mmcfg_config, &mcfg[1], config_size); for (i = 0; i < pci_mmcfg_config_num; ++i) { - if (mcfg->config[i].base_reserved) { + if (pci_mmcfg_config[i].base_reserved) { printk(KERN_ERR PREFIX "MMCONFIG not in low 4GB of memory\n"); kfree(pci_mmcfg_config); @@ -233,11 +233,11 @@ static int __init acpi_parse_madt(struct acpi_table_header *header) return -ENODEV; } - if (madt->lapic_address) { - acpi_lapic_addr = (u64) madt->lapic_address; + if (madt->address) { + acpi_lapic_addr = (u64) madt->address; printk(KERN_DEBUG PREFIX "Local APIC address 0x%08x\n", - madt->lapic_address); + madt->address); } acpi_madt_oem_check(madt->header.oem_id, madt->header.oem_table_id); @@ -654,7 +654,7 @@ static int __init acpi_parse_hpet(struct acpi_table_header *header) return -ENODEV; } - if (hpet_tbl->addr.space_id != ACPI_SPACE_MEM) { + if (hpet_tbl->address.space_id != ACPI_SPACE_MEM) { printk(KERN_WARNING PREFIX "HPET timers must be located in " "memory.\n"); return -1; @@ -667,29 +667,28 @@ static int __init acpi_parse_hpet(struct acpi_table_header *header) hpet_res->name = (void *)&hpet_res[1]; hpet_res->flags = IORESOURCE_MEM | IORESOURCE_BUSY; snprintf((char *)hpet_res->name, HPET_RESOURCE_NAME_SIZE, - "HPET %u", hpet_tbl->number); + "HPET %u", hpet_tbl->sequence); hpet_res->end = (1 * 1024) - 1; } -#ifdef CONFIG_X86_64 - vxtime.hpet_address = hpet_tbl->addr.addrl | - ((long)hpet_tbl->addr.addrh << 32); +#ifdef CONFIG_X86_64 + vxtime.hpet_address = hpet_tbl->address.address; printk(KERN_INFO PREFIX "HPET id: %#x base: %#lx\n", - hpet_tbl->id, vxtime.hpet_address); + hpet_tbl->id, vxtime.hpet_address); res_start = vxtime.hpet_address; -#else /* X86 */ +#else /* X86 */ { extern unsigned long hpet_address; - hpet_address = hpet_tbl->addr.addrl; + hpet_address = hpet_tbl->address.address; printk(KERN_INFO PREFIX "HPET id: %#x base: %#lx\n", - hpet_tbl->id, hpet_address); + hpet_tbl->id, hpet_address); res_start = hpet_address; } -#endif /* X86 */ +#endif /* X86 */ if (hpet_res) { hpet_res->start = res_start; diff --git a/drivers/acpi/ec.c b/drivers/acpi/ec.c index 7a1f2ba..710364e 100644 --- a/drivers/acpi/ec.c +++ b/drivers/acpi/ec.c @@ -889,14 +889,14 @@ static int __init acpi_ec_get_real_ecdt(void) if (acpi_ec_mode == EC_INTR) { init_waitqueue_head(&ec_ecdt->wait); } - ec_ecdt->command_addr = ecdt_ptr->ec_control.address; - ec_ecdt->data_addr = ecdt_ptr->ec_data.address; - ec_ecdt->gpe = ecdt_ptr->gpe_bit; + ec_ecdt->command_addr = ecdt_ptr->control.address; + ec_ecdt->data_addr = ecdt_ptr->data.address; + ec_ecdt->gpe = ecdt_ptr->gpe; /* use the GL just to be safe */ ec_ecdt->global_lock = TRUE; ec_ecdt->uid = ecdt_ptr->uid; - status = acpi_get_handle(NULL, ecdt_ptr->ec_id, &ec_ecdt->handle); + status = acpi_get_handle(NULL, ecdt_ptr->id, &ec_ecdt->handle); if (ACPI_FAILURE(status)) { goto error; } diff --git a/include/acpi/actbl.h b/include/acpi/actbl.h index c5d5ec3..d6af14e 100644 --- a/include/acpi/actbl.h +++ b/include/acpi/actbl.h @@ -289,8 +289,7 @@ enum acpi_prefered_pm_profiles { /* * Get the remaining ACPI tables */ -/* - Don't include any new tables definitions for now. + #include -*/ + #endif /* __ACTBL_H__ */ diff --git a/include/linux/acpi.h b/include/linux/acpi.h index 88cb1fe..5a2b363 100644 --- a/include/linux/acpi.h +++ b/include/linux/acpi.h @@ -60,15 +60,6 @@ typedef struct { /* Multiple APIC Description Table (MADT) */ -struct acpi_table_madt { - struct acpi_table_header header; - u32 lapic_address; - struct { - u32 pcat_compat:1; - u32 reserved:31; - } flags; -} __attribute__ ((packed)); - enum acpi_madt_entry_id { ACPI_MADT_LAPIC = 0, ACPI_MADT_IOAPIC, @@ -185,15 +176,6 @@ struct acpi_gen_regaddr { u32 addrh; } __attribute__ ((packed)); -struct acpi_table_hpet { - struct acpi_table_header header; - u32 id; - struct acpi_gen_regaddr addr; - u8 number; - u16 min_tick; - u8 page_protect; -} __attribute__ ((packed)); - /* * Simple Boot Flags * http://www.microsoft.com/whdc/hwdev/resources/specs/simp_bios.mspx @@ -218,12 +200,6 @@ struct acpi_table_sbf * http://www.microsoft.com/whdc/hwdev/platform/proc/SRAT.mspx */ -struct acpi_table_srat { - struct acpi_table_header header; - u32 table_revision; - u64 reserved; -} __attribute__ ((packed)); - enum acpi_srat_entry_id { ACPI_SRAT_PROCESSOR_AFFINITY = 0, ACPI_SRAT_MEMORY_AFFINITY, @@ -267,36 +243,6 @@ enum acpi_address_range_id { ACPI_ADDRESS_RANGE_COUNT }; -/* - * System Locality Information Table (SLIT) - * see http://devresource.hp.com/devresource/docs/techpapers/ia64/slit.pdf - */ - -struct acpi_table_slit { - struct acpi_table_header header; - u64 localities; - u8 entry[1]; /* real size = localities^2 */ -} __attribute__ ((packed)); - -/* Smart Battery Description Table (SBST) */ - -struct acpi_table_sbst { - struct acpi_table_header header; - u32 warning; /* Warn user */ - u32 low; /* Critical sleep */ - u32 critical; /* Critical shutdown */ -} __attribute__ ((packed)); - -/* Embedded Controller Boot Resources Table (ECDT) */ - -struct acpi_table_ecdt { - struct acpi_table_header header; - struct acpi_generic_address ec_control; - struct acpi_generic_address ec_data; - u32 uid; - u8 gpe_bit; - char ec_id[0]; -} __attribute__ ((packed)); /* PCI MMCONFIG */ @@ -309,11 +255,6 @@ struct acpi_table_mcfg_config { u8 end_bus_number; u8 reserved[4]; } __attribute__ ((packed)); -struct acpi_table_mcfg { - struct acpi_table_header header; - u8 reserved[8]; - struct acpi_table_mcfg_config config[0]; -} __attribute__ ((packed)); /* Table Handlers */ -- cgit v0.10.2 From 5f3b1a8b6737b09ce5df4ec9fad4ad271aecb5fb Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Remove duplicate table definitions (non-conflicting) Signed-off-by: Len Brown diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index 389a8a5..5fafbac 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -66,7 +66,7 @@ static inline int acpi_madt_oem_check(char *oem_id, char *oem_table_id) { return #define BAD_MADT_ENTRY(entry, end) ( \ (!entry) || (unsigned long)entry + sizeof(*entry) > end || \ - ((acpi_table_entry_header *)entry)->length < sizeof(*entry)) + ((struct acpi_subtable_header *)entry)->length < sizeof(*entry)) #define PREFIX "ACPI: " @@ -79,7 +79,7 @@ int acpi_ioapic; int acpi_strict; EXPORT_SYMBOL(acpi_strict); -acpi_interrupt_flags acpi_sci_flags __initdata; +u8 acpi_sci_flags __initdata; int acpi_sci_override_gsi __initdata; int acpi_skip_timer_override __initdata; int acpi_use_timer_override __initdata; @@ -246,11 +246,11 @@ static int __init acpi_parse_madt(struct acpi_table_header *header) } static int __init -acpi_parse_lapic(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_lapic(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_lapic *processor = NULL; + struct acpi_madt_local_apic *processor = NULL; - processor = (struct acpi_table_lapic *)header; + processor = (struct acpi_madt_local_apic *)header; if (BAD_MADT_ENTRY(processor, end)) return -EINVAL; @@ -258,8 +258,8 @@ acpi_parse_lapic(acpi_table_entry_header * header, const unsigned long end) acpi_table_print_madt_entry(header); /* Record local apic id only when enabled */ - if (processor->flags.enabled) - x86_acpiid_to_apicid[processor->acpi_id] = processor->id; + if (processor->lapic_flags & ACPI_MADT_ENABLED) + x86_acpiid_to_apicid[processor->processor_id] = processor->id; /* * We need to register disabled CPU as well to permit @@ -269,18 +269,18 @@ acpi_parse_lapic(acpi_table_entry_header * header, const unsigned long end) * when we use CPU hotplug. */ mp_register_lapic(processor->id, /* APIC ID */ - processor->flags.enabled); /* Enabled? */ + processor->lapic_flags & ACPI_MADT_ENABLED); /* Enabled? */ return 0; } static int __init -acpi_parse_lapic_addr_ovr(acpi_table_entry_header * header, +acpi_parse_lapic_addr_ovr(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_lapic_addr_ovr *lapic_addr_ovr = NULL; + struct acpi_madt_local_apic_override *lapic_addr_ovr = NULL; - lapic_addr_ovr = (struct acpi_table_lapic_addr_ovr *)header; + lapic_addr_ovr = (struct acpi_madt_local_apic_override *)header; if (BAD_MADT_ENTRY(lapic_addr_ovr, end)) return -EINVAL; @@ -291,11 +291,11 @@ acpi_parse_lapic_addr_ovr(acpi_table_entry_header * header, } static int __init -acpi_parse_lapic_nmi(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_lapic_nmi(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_lapic_nmi *lapic_nmi = NULL; + struct acpi_madt_local_apic_nmi *lapic_nmi = NULL; - lapic_nmi = (struct acpi_table_lapic_nmi *)header; + lapic_nmi = (struct acpi_madt_local_apic_nmi *)header; if (BAD_MADT_ENTRY(lapic_nmi, end)) return -EINVAL; @@ -313,11 +313,11 @@ acpi_parse_lapic_nmi(acpi_table_entry_header * header, const unsigned long end) #ifdef CONFIG_X86_IO_APIC static int __init -acpi_parse_ioapic(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_ioapic(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_ioapic *ioapic = NULL; + struct acpi_madt_io_apic *ioapic = NULL; - ioapic = (struct acpi_table_ioapic *)header; + ioapic = (struct acpi_madt_io_apic *)header; if (BAD_MADT_ENTRY(ioapic, end)) return -EINVAL; @@ -342,11 +342,11 @@ static void __init acpi_sci_ioapic_setup(u32 gsi, u16 polarity, u16 trigger) polarity = 3; /* Command-line over-ride via acpi_sci= */ - if (acpi_sci_flags.trigger) - trigger = acpi_sci_flags.trigger; + if (acpi_sci_flags & ACPI_MADT_TRIGGER_MASK) + trigger = (acpi_sci_flags & ACPI_MADT_TRIGGER_MASK) >> 2; - if (acpi_sci_flags.polarity) - polarity = acpi_sci_flags.polarity; + if (acpi_sci_flags & ACPI_MADT_POLARITY_MASK) + polarity = acpi_sci_flags & ACPI_MADT_POLARITY_MASK; /* * mp_config_acpi_legacy_irqs() already setup IRQs < 16 @@ -364,44 +364,45 @@ static void __init acpi_sci_ioapic_setup(u32 gsi, u16 polarity, u16 trigger) } static int __init -acpi_parse_int_src_ovr(acpi_table_entry_header * header, +acpi_parse_int_src_ovr(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_int_src_ovr *intsrc = NULL; + struct acpi_madt_interrupt_override *intsrc = NULL; - intsrc = (struct acpi_table_int_src_ovr *)header; + intsrc = (struct acpi_madt_interrupt_override *)header; if (BAD_MADT_ENTRY(intsrc, end)) return -EINVAL; acpi_table_print_madt_entry(header); - if (intsrc->bus_irq == acpi_gbl_FADT.sci_interrupt) { + if (intsrc->source_irq == acpi_gbl_FADT.sci_interrupt) { acpi_sci_ioapic_setup(intsrc->global_irq, - intsrc->flags.polarity, - intsrc->flags.trigger); + intsrc->inti_flags & ACPI_MADT_POLARITY_MASK, + (intsrc->inti_flags & ACPI_MADT_TRIGGER_MASK) >> 2); return 0; } if (acpi_skip_timer_override && - intsrc->bus_irq == 0 && intsrc->global_irq == 2) { + intsrc->source_irq == 0 && intsrc->global_irq == 2) { printk(PREFIX "BIOS IRQ0 pin2 override ignored.\n"); return 0; } - mp_override_legacy_irq(intsrc->bus_irq, - intsrc->flags.polarity, - intsrc->flags.trigger, intsrc->global_irq); + mp_override_legacy_irq(intsrc->source_irq, + intsrc->inti_flags & ACPI_MADT_POLARITY_MASK, + (intsrc->inti_flags & ACPI_MADT_TRIGGER_MASK) >> 2, + intsrc->global_irq); return 0; } static int __init -acpi_parse_nmi_src(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_nmi_src(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_nmi_src *nmi_src = NULL; + struct acpi_madt_nmi_source *nmi_src = NULL; - nmi_src = (struct acpi_table_nmi_src *)header; + nmi_src = (struct acpi_madt_nmi_source *)header; if (BAD_MADT_ENTRY(nmi_src, end)) return -EINVAL; @@ -417,7 +418,7 @@ acpi_parse_nmi_src(acpi_table_entry_header * header, const unsigned long end) /* * acpi_pic_sci_set_trigger() - * + * * use ELCR to set PIC-mode trigger type for SCI * * If a PIC-mode SCI is not recognized or gives spurious IRQ7's @@ -511,7 +512,7 @@ int acpi_map_lsapic(acpi_handle handle, int *pcpu) { struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; union acpi_object *obj; - struct acpi_table_lapic *lapic; + struct acpi_madt_local_apic *lapic; cpumask_t tmp_map, new_map; u8 physid; int cpu; @@ -529,10 +530,10 @@ int acpi_map_lsapic(acpi_handle handle, int *pcpu) return -EINVAL; } - lapic = (struct acpi_table_lapic *)obj->buffer.pointer; + lapic = (struct acpi_madt_local_apic *)obj->buffer.pointer; - if ((lapic->header.type != ACPI_MADT_LAPIC) || - (!lapic->flags.enabled)) { + if (lapic->header.type != ACPI_MADT_TYPE_LOCAL_APIC || + !(lapic->lapic_flags & ACPI_MADT_ENABLED)) { kfree(buffer.pointer); return -EINVAL; } @@ -544,7 +545,7 @@ int acpi_map_lsapic(acpi_handle handle, int *pcpu) buffer.pointer = NULL; tmp_map = cpu_present_map; - mp_register_lapic(physid, lapic->flags.enabled); + mp_register_lapic(physid, lapic->lapic_flags & ACPI_MADT_ENABLED); /* * If mp_register_lapic successfully generates a new logical cpu @@ -619,36 +620,30 @@ acpi_scan_rsdp(unsigned long start, unsigned long length) return 0; } -static int __init acpi_parse_sbf(struct acpi_table_header *header) +static int __init acpi_parse_sbf(struct acpi_table_header *table) { - struct acpi_table_sbf *sb; - - if (!header) - return -EINVAL; + struct acpi_table_boot *sb; - sb = (struct acpi_table_sbf *)header; + sb = (struct acpi_table_boot *)table; if (!sb) { printk(KERN_WARNING PREFIX "Unable to map SBF\n"); return -ENODEV; } - sbf_port = sb->sbf_cmos; /* Save CMOS port */ + sbf_port = sb->cmos_index; /* Save CMOS port */ return 0; } #ifdef CONFIG_HPET_TIMER -static int __init acpi_parse_hpet(struct acpi_table_header *header) +static int __init acpi_parse_hpet(struct acpi_table_header *table) { struct acpi_table_hpet *hpet_tbl; struct resource *hpet_res; resource_size_t res_start; - if (!header) - return -EINVAL; - - hpet_tbl = (struct acpi_table_hpet *)header; + hpet_tbl = (struct acpi_table_hpet *)table; if (!hpet_tbl) { printk(KERN_WARNING PREFIX "Unable to map HPET\n"); return -ENODEV; @@ -706,35 +701,28 @@ static int __init acpi_parse_hpet(struct acpi_table_header *header) extern u32 pmtmr_ioport; #endif -static int __init acpi_parse_fadt(struct acpi_table_header *header) +static int __init acpi_parse_fadt(struct acpi_table_header *table) { - struct acpi_table_fadt *fadt = NULL; - - fadt = (struct acpi_table_fadt *)header; - if (!fadt) { - printk(KERN_WARNING PREFIX "Unable to map FADT\n"); - return 0; - } #ifdef CONFIG_X86_PM_TIMER /* detect the location of the ACPI PM Timer */ - if (fadt->header.revision >= FADT2_REVISION_ID) { + if (acpi_gbl_FADT.header.revision >= FADT2_REVISION_ID) { /* FADT rev. 2 */ - if (fadt->xpm_timer_block.space_id != + if (acpi_gbl_FADT.xpm_timer_block.space_id != ACPI_ADR_SPACE_SYSTEM_IO) return 0; - pmtmr_ioport = fadt->xpm_timer_block.address; + pmtmr_ioport = acpi_gbl_FADT.xpm_timer_block.address; /* * "X" fields are optional extensions to the original V1.0 * fields, so we must selectively expand V1.0 fields if the * corresponding X field is zero. */ if (!pmtmr_ioport) - pmtmr_ioport = fadt->pm_timer_block; + pmtmr_ioport = acpi_gbl_FADT.pm_timer_block; } else { /* FADT rev. 1 */ - pmtmr_ioport = fadt->pm_timer_block; + pmtmr_ioport = acpi_gbl_FADT.pm_timer_block; } if (pmtmr_ioport) printk(KERN_INFO PREFIX "PM-Timer IO Port: %#x\n", @@ -776,13 +764,13 @@ static int __init acpi_parse_madt_lapic_entries(void) if (!cpu_has_apic) return -ENODEV; - /* + /* * Note that the LAPIC address is obtained from the MADT (32-bit value) * and (optionally) overriden by a LAPIC_ADDR_OVR entry (64-bit value). */ count = - acpi_table_parse_madt(ACPI_MADT_LAPIC_ADDR_OVR, + acpi_table_parse_madt(ACPI_MADT_TYPE_LOCAL_APIC_OVERRIDE, acpi_parse_lapic_addr_ovr, 0); if (count < 0) { printk(KERN_ERR PREFIX @@ -792,7 +780,7 @@ static int __init acpi_parse_madt_lapic_entries(void) mp_register_lapic_address(acpi_lapic_addr); - count = acpi_table_parse_madt(ACPI_MADT_LAPIC, acpi_parse_lapic, + count = acpi_table_parse_madt(ACPI_MADT_TYPE_LOCAL_APIC, acpi_parse_lapic, MAX_APICS); if (!count) { printk(KERN_ERR PREFIX "No LAPIC entries present\n"); @@ -805,7 +793,7 @@ static int __init acpi_parse_madt_lapic_entries(void) } count = - acpi_table_parse_madt(ACPI_MADT_LAPIC_NMI, acpi_parse_lapic_nmi, 0); + acpi_table_parse_madt(ACPI_MADT_TYPE_LOCAL_APIC_NMI, acpi_parse_lapic_nmi, 0); if (count < 0) { printk(KERN_ERR PREFIX "Error parsing LAPIC NMI entry\n"); /* TBD: Cleanup to allow fallback to MPS */ @@ -834,7 +822,7 @@ static int __init acpi_parse_madt_ioapic_entries(void) return -ENODEV; } - if (!cpu_has_apic) + if (!cpu_has_apic) return -ENODEV; /* @@ -847,7 +835,7 @@ static int __init acpi_parse_madt_ioapic_entries(void) } count = - acpi_table_parse_madt(ACPI_MADT_IOAPIC, acpi_parse_ioapic, + acpi_table_parse_madt(ACPI_MADT_TYPE_IO_APIC, acpi_parse_ioapic, MAX_IO_APICS); if (!count) { printk(KERN_ERR PREFIX "No IOAPIC entries present\n"); @@ -858,7 +846,7 @@ static int __init acpi_parse_madt_ioapic_entries(void) } count = - acpi_table_parse_madt(ACPI_MADT_INT_SRC_OVR, acpi_parse_int_src_ovr, + acpi_table_parse_madt(ACPI_MADT_TYPE_INTERRUPT_OVERRIDE, acpi_parse_int_src_ovr, NR_IRQ_VECTORS); if (count < 0) { printk(KERN_ERR PREFIX @@ -878,7 +866,7 @@ static int __init acpi_parse_madt_ioapic_entries(void) mp_config_acpi_legacy_irqs(); count = - acpi_table_parse_madt(ACPI_MADT_NMI_SRC, acpi_parse_nmi_src, + acpi_table_parse_madt(ACPI_MADT_TYPE_NMI_SOURCE, acpi_parse_nmi_src, NR_IRQ_VECTORS); if (count < 0) { printk(KERN_ERR PREFIX "Error parsing NMI SRC entry\n"); @@ -900,7 +888,7 @@ static void __init acpi_process_madt(void) #ifdef CONFIG_X86_LOCAL_APIC int count, error; - count = acpi_table_parse("APIC", acpi_parse_madt); + count = acpi_table_parse(ACPI_SIG_MADT, acpi_parse_madt); if (count >= 1) { /* @@ -1187,7 +1175,7 @@ int __init acpi_boot_table_init(void) if (acpi_disabled && !acpi_ht) return 1; - /* + /* * Initialize the ACPI boot-time table parser. */ error = acpi_table_init(); @@ -1196,7 +1184,7 @@ int __init acpi_boot_table_init(void) return error; } - acpi_table_parse("BOOT", acpi_parse_sbf); + acpi_table_parse(ACPI_SIG_BOOT, acpi_parse_sbf); /* * blacklist may disable ACPI entirely @@ -1224,7 +1212,7 @@ int __init acpi_boot_init(void) if (acpi_disabled && !acpi_ht) return 1; - acpi_table_parse("BOOT", acpi_parse_sbf); + acpi_table_parse(ACPI_SIG_BOOT, acpi_parse_sbf); /* * set sci_int and PM timer address @@ -1236,7 +1224,7 @@ int __init acpi_boot_init(void) */ acpi_process_madt(); - acpi_table_parse("HPET", acpi_parse_hpet); + acpi_table_parse(ACPI_SIG_HPET, acpi_parse_hpet); return 0; } @@ -1307,13 +1295,17 @@ static int __init setup_acpi_sci(char *s) if (!s) return -EINVAL; if (!strcmp(s, "edge")) - acpi_sci_flags.trigger = 1; + acpi_sci_flags = ACPI_MADT_TRIGGER_EDGE | + (acpi_sci_flags & ~ACPI_MADT_TRIGGER_MASK); else if (!strcmp(s, "level")) - acpi_sci_flags.trigger = 3; + acpi_sci_flags = ACPI_MADT_TRIGGER_LEVEL | + (acpi_sci_flags & ~ACPI_MADT_TRIGGER_MASK); else if (!strcmp(s, "high")) - acpi_sci_flags.polarity = 1; + acpi_sci_flags = ACPI_MADT_POLARITY_ACTIVE_HIGH | + (acpi_sci_flags & ~ACPI_MADT_POLARITY_MASK); else if (!strcmp(s, "low")) - acpi_sci_flags.polarity = 3; + acpi_sci_flags = ACPI_MADT_POLARITY_ACTIVE_LOW | + (acpi_sci_flags & ~ACPI_MADT_POLARITY_MASK); else return -EINVAL; return 0; diff --git a/arch/ia64/kernel/acpi.c b/arch/ia64/kernel/acpi.c index d37fb8e..4719e48 100644 --- a/arch/ia64/kernel/acpi.c +++ b/arch/ia64/kernel/acpi.c @@ -55,7 +55,7 @@ #define BAD_MADT_ENTRY(entry, end) ( \ (!entry) || (unsigned long)entry + sizeof(*entry) > end || \ - ((acpi_table_entry_header *)entry)->length < sizeof(*entry)) + ((struct acpi_subtable_header *)entry)->length < sizeof(*entry)) #define PREFIX "ACPI: " @@ -94,7 +94,7 @@ const char *acpi_get_sysname(void) return "dig"; } - xsdt = (struct acpi_table_xsdt *)__va(rsdp->xsdt_address); + xsdt = (struct acpi_table_xsdt *)__va(rsdp->xsdt_physical_address); hdr = &xsdt->header; if (strncmp(hdr->signature, ACPI_SIG_XSDT, sizeof(ACPI_SIG_XSDT) - 1)) { printk(KERN_ERR @@ -169,12 +169,12 @@ struct acpi_table_madt *acpi_madt __initdata; static u8 has_8259; static int __init -acpi_parse_lapic_addr_ovr(acpi_table_entry_header * header, +acpi_parse_lapic_addr_ovr(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_lapic_addr_ovr *lapic; + struct acpi_madt_local_apic_override *lapic; - lapic = (struct acpi_table_lapic_addr_ovr *)header; + lapic = (struct acpi_madt_local_apic_override *)header; if (BAD_MADT_ENTRY(lapic, end)) return -EINVAL; @@ -187,21 +187,20 @@ acpi_parse_lapic_addr_ovr(acpi_table_entry_header * header, } static int __init -acpi_parse_lsapic(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_lsapic(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_lsapic *lsapic; + struct acpi_madt_local_sapic *lsapic; - lsapic = (struct acpi_table_lsapic *)header; + lsapic = (struct acpi_madt_local_sapic *)header; - if (BAD_MADT_ENTRY(lsapic, end)) - return -EINVAL; + /*Skip BAD_MADT_ENTRY check, as lsapic size could vary */ - if (lsapic->flags.enabled) { + if (lsapic->lapic_flags & ACPI_MADT_ENABLED) { #ifdef CONFIG_SMP smp_boot_data.cpu_phys_id[available_cpus] = (lsapic->id << 8) | lsapic->eid; #endif - ia64_acpiid_to_sapicid[lsapic->acpi_id] = + ia64_acpiid_to_sapicid[lsapic->processor_id] = (lsapic->id << 8) | lsapic->eid; ++available_cpus; } @@ -211,11 +210,11 @@ acpi_parse_lsapic(acpi_table_entry_header * header, const unsigned long end) } static int __init -acpi_parse_lapic_nmi(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_lapic_nmi(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_lapic_nmi *lacpi_nmi; + struct acpi_madt_local_apic_nmi *lacpi_nmi; - lacpi_nmi = (struct acpi_table_lapic_nmi *)header; + lacpi_nmi = (struct acpi_madt_local_apic_nmi *)header; if (BAD_MADT_ENTRY(lacpi_nmi, end)) return -EINVAL; @@ -225,11 +224,11 @@ acpi_parse_lapic_nmi(acpi_table_entry_header * header, const unsigned long end) } static int __init -acpi_parse_iosapic(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_iosapic(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_iosapic *iosapic; + struct acpi_madt_io_sapic *iosapic; - iosapic = (struct acpi_table_iosapic *)header; + iosapic = (struct acpi_madt_io_sapic *)header; if (BAD_MADT_ENTRY(iosapic, end)) return -EINVAL; @@ -240,13 +239,13 @@ acpi_parse_iosapic(acpi_table_entry_header * header, const unsigned long end) static unsigned int __initdata acpi_madt_rev; static int __init -acpi_parse_plat_int_src(acpi_table_entry_header * header, +acpi_parse_plat_int_src(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_plat_int_src *plintsrc; + struct acpi_madt_interrupt_source *plintsrc; int vector; - plintsrc = (struct acpi_table_plat_int_src *)header; + plintsrc = (struct acpi_madt_interrupt_source *)header; if (BAD_MADT_ENTRY(plintsrc, end)) return -EINVAL; @@ -257,19 +256,19 @@ acpi_parse_plat_int_src(acpi_table_entry_header * header, */ vector = iosapic_register_platform_intr(plintsrc->type, plintsrc->global_irq, - plintsrc->iosapic_vector, + plintsrc->io_sapic_vector, plintsrc->eid, plintsrc->id, - (plintsrc->flags.polarity == - 1) ? IOSAPIC_POL_HIGH : - IOSAPIC_POL_LOW, - (plintsrc->flags.trigger == - 1) ? IOSAPIC_EDGE : - IOSAPIC_LEVEL); + ((plintsrc->inti_flags & ACPI_MADT_POLARITY_MASK) == + ACPI_MADT_POLARITY_ACTIVE_HIGH) ? + IOSAPIC_POL_HIGH : IOSAPIC_POL_LOW, + ((plintsrc->inti_flags & ACPI_MADT_TRIGGER_MASK) == + ACPI_MADT_TRIGGER_EDGE) ? + IOSAPIC_EDGE : IOSAPIC_LEVEL); platform_intr_list[plintsrc->type] = vector; if (acpi_madt_rev > 1) { - acpi_cpei_override = plintsrc->plint_flags.cpei_override_flag; + acpi_cpei_override = plintsrc->flags & ACPI_MADT_CPEI_OVERRIDE; } /* @@ -324,30 +323,32 @@ unsigned int get_cpei_target_cpu(void) } static int __init -acpi_parse_int_src_ovr(acpi_table_entry_header * header, +acpi_parse_int_src_ovr(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_int_src_ovr *p; + struct acpi_madt_interrupt_override *p; - p = (struct acpi_table_int_src_ovr *)header; + p = (struct acpi_madt_interrupt_override *)header; if (BAD_MADT_ENTRY(p, end)) return -EINVAL; - iosapic_override_isa_irq(p->bus_irq, p->global_irq, - (p->flags.polarity == - 1) ? IOSAPIC_POL_HIGH : IOSAPIC_POL_LOW, - (p->flags.trigger == - 1) ? IOSAPIC_EDGE : IOSAPIC_LEVEL); + iosapic_override_isa_irq(p->source_irq, p->global_irq, + ((p->inti_flags & ACPI_MADT_POLARITY_MASK) == + ACPI_MADT_POLARITY_ACTIVE_HIGH) ? + IOSAPIC_POL_HIGH : IOSAPIC_POL_LOW, + ((p->inti_flags & ACPI_MADT_TRIGGER_MASK) == + ACPI_MADT_TRIGGER_EDGE) ? + IOSAPIC_EDGE : IOSAPIC_LEVEL); return 0; } static int __init -acpi_parse_nmi_src(acpi_table_entry_header * header, const unsigned long end) +acpi_parse_nmi_src(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_nmi_src *nmi_src; + struct acpi_madt_nmi_source *nmi_src; - nmi_src = (struct acpi_table_nmi_src *)header; + nmi_src = (struct acpi_madt_nmi_source *)header; if (BAD_MADT_ENTRY(nmi_src, end)) return -EINVAL; @@ -371,12 +372,12 @@ static void __init acpi_madt_oem_check(char *oem_id, char *oem_table_id) } } -static int __init acpi_parse_madt(unsigned long phys_addr, unsigned long size) +static int __init acpi_parse_madt(struct acpi_table_header *table) { - if (!phys_addr || !size) + if (!table) return -EINVAL; - acpi_madt = (struct acpi_table_madt *)__va(phys_addr); + acpi_madt = (struct acpi_table_madt *)table; acpi_madt_rev = acpi_madt->header.revision; @@ -384,14 +385,14 @@ static int __init acpi_parse_madt(unsigned long phys_addr, unsigned long size) #ifdef CONFIG_ITANIUM has_8259 = 1; /* Firmware on old Itanium systems is broken */ #else - has_8259 = acpi_madt->flags.pcat_compat; + has_8259 = acpi_madt->flags & ACPI_MADT_PCAT_COMPAT; #endif iosapic_system_init(has_8259); /* Get base address of IPI Message Block */ - if (acpi_madt->lapic_address) - ipi_base_addr = ioremap(acpi_madt->lapic_address, 0); + if (acpi_madt->address) + ipi_base_addr = ioremap(acpi_madt->address, 0); printk(KERN_INFO PREFIX "Local APIC address %p\n", ipi_base_addr); @@ -413,23 +414,24 @@ static u32 __devinitdata pxm_flag[PXM_FLAG_LEN]; #define pxm_bit_test(bit) (test_bit(bit,(void *)pxm_flag)) static struct acpi_table_slit __initdata *slit_table; -static int get_processor_proximity_domain(struct acpi_table_processor_affinity *pa) +static int get_processor_proximity_domain(struct acpi_srat_cpu_affinity *pa) { int pxm; - pxm = pa->proximity_domain; + pxm = pa->proximity_domain_lo; if (ia64_platform_is("sn2")) - pxm += pa->reserved[0] << 8; + pxm += pa->proximity_domain_hi[0] << 8; return pxm; } -static int get_memory_proximity_domain(struct acpi_table_memory_affinity *ma) +static int get_memory_proximity_domain(struct acpi_srat_mem_affinity *ma) { int pxm; pxm = ma->proximity_domain; if (ia64_platform_is("sn2")) - pxm += ma->reserved1[0] << 8; + pxm += ma->reserved << 8; + return pxm; } @@ -442,7 +444,7 @@ void __init acpi_numa_slit_init(struct acpi_table_slit *slit) u32 len; len = sizeof(struct acpi_table_header) + 8 - + slit->localities * slit->localities; + + slit->locality_count * slit->locality_count; if (slit->header.length != len) { printk(KERN_ERR "ACPI 2.0 SLIT: size mismatch: %d expected, %d actual\n", @@ -454,11 +456,11 @@ void __init acpi_numa_slit_init(struct acpi_table_slit *slit) } void __init -acpi_numa_processor_affinity_init(struct acpi_table_processor_affinity *pa) +acpi_numa_processor_affinity_init(struct acpi_srat_cpu_affinity *pa) { int pxm; - if (!pa->flags.enabled) + if (!(pa->flags & ACPI_SRAT_CPU_ENABLED)) return; pxm = get_processor_proximity_domain(pa); @@ -467,14 +469,14 @@ acpi_numa_processor_affinity_init(struct acpi_table_processor_affinity *pa) pxm_bit_set(pxm); node_cpuid[srat_num_cpus].phys_id = - (pa->apic_id << 8) | (pa->lsapic_eid); + (pa->apic_id << 8) | (pa->local_sapic_eid); /* nid should be overridden as logical node id later */ node_cpuid[srat_num_cpus].nid = pxm; srat_num_cpus++; } void __init -acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma) +acpi_numa_memory_affinity_init(struct acpi_srat_mem_affinity *ma) { unsigned long paddr, size; int pxm; @@ -483,13 +485,11 @@ acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma) pxm = get_memory_proximity_domain(ma); /* fill node memory chunk structure */ - paddr = ma->base_addr_hi; - paddr = (paddr << 32) | ma->base_addr_lo; - size = ma->length_hi; - size = (size << 32) | ma->length_lo; + paddr = ma->base_address; + size = ma->length; /* Ignore disabled entries */ - if (!ma->flags.enabled) + if (!(ma->flags & ACPI_SRAT_MEM_ENABLED)) return; /* record this node in proximity bitmap */ @@ -560,16 +560,16 @@ void __init acpi_numa_arch_fixup(void) if (!slit_table) return; memset(numa_slit, -1, sizeof(numa_slit)); - for (i = 0; i < slit_table->localities; i++) { + for (i = 0; i < slit_table->locality_count; i++) { if (!pxm_bit_test(i)) continue; node_from = pxm_to_node(i); - for (j = 0; j < slit_table->localities; j++) { + for (j = 0; j < slit_table->locality_count; j++) { if (!pxm_bit_test(j)) continue; node_to = pxm_to_node(j); node_distance(node_from, node_to) = - slit_table->entry[i * slit_table->localities + j]; + slit_table->entry[i * slit_table->locality_count + j]; } } @@ -614,15 +614,15 @@ void acpi_unregister_gsi(u32 gsi) EXPORT_SYMBOL(acpi_unregister_gsi); -static int __init acpi_parse_fadt(unsigned long phys_addr, unsigned long size) +static int __init acpi_parse_fadt(struct acpi_table_header *table) { struct acpi_table_header *fadt_header; struct acpi_table_fadt *fadt; - if (!phys_addr || !size) + if (!table) return -EINVAL; - fadt_header = (struct acpi_table_header *)__va(phys_addr); + fadt_header = (struct acpi_table_header *)table; if (fadt_header->revision != 3) return -ENODEV; /* Only deal with ACPI 2.0 FADT */ @@ -655,7 +655,7 @@ int __init acpi_boot_init(void) * information -- the successor to MPS tables. */ - if (acpi_table_parse(ACPI_APIC, acpi_parse_madt) < 1) { + if (acpi_table_parse(ACPI_SIG_MADT, acpi_parse_madt) < 1) { printk(KERN_ERR PREFIX "Can't find MADT\n"); goto skip_madt; } @@ -663,40 +663,40 @@ int __init acpi_boot_init(void) /* Local APIC */ if (acpi_table_parse_madt - (ACPI_MADT_LAPIC_ADDR_OVR, acpi_parse_lapic_addr_ovr, 0) < 0) + (ACPI_MADT_TYPE_LOCAL_APIC_OVERRIDE, acpi_parse_lapic_addr_ovr, 0) < 0) printk(KERN_ERR PREFIX "Error parsing LAPIC address override entry\n"); - if (acpi_table_parse_madt(ACPI_MADT_LSAPIC, acpi_parse_lsapic, NR_CPUS) + if (acpi_table_parse_madt(ACPI_MADT_TYPE_LOCAL_SAPIC, acpi_parse_lsapic, NR_CPUS) < 1) printk(KERN_ERR PREFIX "Error parsing MADT - no LAPIC entries\n"); - if (acpi_table_parse_madt(ACPI_MADT_LAPIC_NMI, acpi_parse_lapic_nmi, 0) + if (acpi_table_parse_madt(ACPI_MADT_TYPE_LOCAL_APIC_NMI, acpi_parse_lapic_nmi, 0) < 0) printk(KERN_ERR PREFIX "Error parsing LAPIC NMI entry\n"); /* I/O APIC */ if (acpi_table_parse_madt - (ACPI_MADT_IOSAPIC, acpi_parse_iosapic, NR_IOSAPICS) < 1) + (ACPI_MADT_TYPE_IO_SAPIC, acpi_parse_iosapic, NR_IOSAPICS) < 1) printk(KERN_ERR PREFIX "Error parsing MADT - no IOSAPIC entries\n"); /* System-Level Interrupt Routing */ if (acpi_table_parse_madt - (ACPI_MADT_PLAT_INT_SRC, acpi_parse_plat_int_src, + (ACPI_MADT_TYPE_INTERRUPT_SOURCE, acpi_parse_plat_int_src, ACPI_MAX_PLATFORM_INTERRUPTS) < 0) printk(KERN_ERR PREFIX "Error parsing platform interrupt source entry\n"); if (acpi_table_parse_madt - (ACPI_MADT_INT_SRC_OVR, acpi_parse_int_src_ovr, 0) < 0) + (ACPI_MADT_TYPE_INTERRUPT_OVERRIDE, acpi_parse_int_src_ovr, 0) < 0) printk(KERN_ERR PREFIX "Error parsing interrupt source overrides entry\n"); - if (acpi_table_parse_madt(ACPI_MADT_NMI_SRC, acpi_parse_nmi_src, 0) < 0) + if (acpi_table_parse_madt(ACPI_MADT_TYPE_NMI_SOURCE, acpi_parse_nmi_src, 0) < 0) printk(KERN_ERR PREFIX "Error parsing NMI SRC entry\n"); skip_madt: @@ -706,7 +706,7 @@ int __init acpi_boot_init(void) * gets interrupts such as power and sleep buttons. If it's not * on a Legacy interrupt, it needs to be setup. */ - if (acpi_table_parse(ACPI_FADT, acpi_parse_fadt) < 1) + if (acpi_table_parse(ACPI_SIG_FADT, acpi_parse_fadt) < 1) printk(KERN_ERR PREFIX "Can't find FADT\n"); #ifdef CONFIG_SMP @@ -839,7 +839,7 @@ int acpi_map_lsapic(acpi_handle handle, int *pcpu) { struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; union acpi_object *obj; - struct acpi_table_lsapic *lsapic; + struct acpi_madt_local_sapic *lsapic; cpumask_t tmp_map; long physid; int cpu; @@ -851,16 +851,16 @@ int acpi_map_lsapic(acpi_handle handle, int *pcpu) return -EINVAL; obj = buffer.pointer; - if (obj->type != ACPI_TYPE_BUFFER || - obj->buffer.length < sizeof(*lsapic)) { + if (obj->type != ACPI_TYPE_BUFFER) + { kfree(buffer.pointer); return -EINVAL; } - lsapic = (struct acpi_table_lsapic *)obj->buffer.pointer; + lsapic = (struct acpi_madt_local_sapic *)obj->buffer.pointer; - if ((lsapic->header.type != ACPI_MADT_LSAPIC) || - (!lsapic->flags.enabled)) { + if ((lsapic->header.type != ACPI_MADT_TYPE_LOCAL_SAPIC) || + (!lsapic->lapic_flags & ACPI_MADT_ENABLED)) { kfree(buffer.pointer); return -EINVAL; } @@ -880,7 +880,7 @@ int acpi_map_lsapic(acpi_handle handle, int *pcpu) cpu_set(cpu, cpu_present_map); ia64_cpu_to_sapicid[cpu] = physid; - ia64_acpiid_to_sapicid[lsapic->acpi_id] = ia64_cpu_to_sapicid[cpu]; + ia64_acpiid_to_sapicid[lsapic->processor_id] = ia64_cpu_to_sapicid[cpu]; *pcpu = cpu; return (0); @@ -917,7 +917,7 @@ acpi_map_iosapic(acpi_handle handle, u32 depth, void *context, void **ret) { struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; union acpi_object *obj; - struct acpi_table_iosapic *iosapic; + struct acpi_madt_io_sapic *iosapic; unsigned int gsi_base; int pxm, node; @@ -935,9 +935,9 @@ acpi_map_iosapic(acpi_handle handle, u32 depth, void *context, void **ret) return AE_OK; } - iosapic = (struct acpi_table_iosapic *)obj->buffer.pointer; + iosapic = (struct acpi_madt_io_sapic *)obj->buffer.pointer; - if (iosapic->header.type != ACPI_MADT_IOSAPIC) { + if (iosapic->header.type != ACPI_MADT_TYPE_IO_SAPIC) { kfree(buffer.pointer); return AE_OK; } diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c index 324b099..15d677e 100644 --- a/drivers/acpi/bus.c +++ b/drivers/acpi/bus.c @@ -620,15 +620,16 @@ void __init acpi_early_init(void) #ifdef CONFIG_X86 if (!acpi_ioapic) { - extern acpi_interrupt_flags acpi_sci_flags; + extern u8 acpi_sci_flags; /* compatible (0) means level (3) */ - if (acpi_sci_flags.trigger == 0) - acpi_sci_flags.trigger = 3; - + if (!(acpi_sci_flags & ACPI_MADT_TRIGGER_MASK)) { + acpi_sci_flags &= ~ACPI_MADT_TRIGGER_MASK; + acpi_sci_flags |= ACPI_MADT_TRIGGER_LEVEL; + } /* Set PIC-mode SCI trigger type */ acpi_pic_sci_set_trigger(acpi_gbl_FADT.sci_interrupt, - acpi_sci_flags.trigger); + (acpi_sci_flags & ACPI_MADT_TRIGGER_MASK) >> 2); } else { extern int acpi_sci_override_gsi; /* diff --git a/drivers/acpi/tables.c b/drivers/acpi/tables.c index 962ff29..ba4cb20 100644 --- a/drivers/acpi/tables.c +++ b/drivers/acpi/tables.c @@ -43,90 +43,92 @@ static char *mps_inti_flags_trigger[] = { "dfl", "edge", "res", "level" }; static struct acpi_table_desc initial_tables[ACPI_MAX_TABLES] __initdata; -void acpi_table_print_madt_entry(acpi_table_entry_header * header) +void acpi_table_print_madt_entry(struct acpi_subtable_header * header) { if (!header) return; switch (header->type) { - case ACPI_MADT_LAPIC: + case ACPI_MADT_TYPE_LOCAL_APIC: { - struct acpi_table_lapic *p = - (struct acpi_table_lapic *)header; + struct acpi_madt_local_apic *p = + (struct acpi_madt_local_apic *)header; printk(KERN_INFO PREFIX "LAPIC (acpi_id[0x%02x] lapic_id[0x%02x] %s)\n", - p->acpi_id, p->id, - p->flags.enabled ? "enabled" : "disabled"); + p->processor_id, p->id, + (p->lapic_flags & ACPI_MADT_ENABLED) ? "enabled" : "disabled"); } break; - case ACPI_MADT_IOAPIC: + case ACPI_MADT_TYPE_IO_APIC: { - struct acpi_table_ioapic *p = - (struct acpi_table_ioapic *)header; + struct acpi_madt_io_apic *p = + (struct acpi_madt_io_apic *)header; printk(KERN_INFO PREFIX "IOAPIC (id[0x%02x] address[0x%08x] gsi_base[%d])\n", p->id, p->address, p->global_irq_base); } break; - case ACPI_MADT_INT_SRC_OVR: + case ACPI_MADT_TYPE_INTERRUPT_OVERRIDE: { - struct acpi_table_int_src_ovr *p = - (struct acpi_table_int_src_ovr *)header; + struct acpi_madt_interrupt_override *p = + (struct acpi_madt_interrupt_override *)header; printk(KERN_INFO PREFIX "INT_SRC_OVR (bus %d bus_irq %d global_irq %d %s %s)\n", - p->bus, p->bus_irq, p->global_irq, - mps_inti_flags_polarity[p->flags.polarity], - mps_inti_flags_trigger[p->flags.trigger]); - if (p->flags.reserved) + p->bus, p->source_irq, p->global_irq, + mps_inti_flags_polarity[p->inti_flags & ACPI_MADT_POLARITY_MASK], + mps_inti_flags_trigger[(p->inti_flags & ACPI_MADT_TRIGGER_MASK) >> 2]); + if (p->inti_flags & + ~(ACPI_MADT_POLARITY_MASK | ACPI_MADT_TRIGGER_MASK)) printk(KERN_INFO PREFIX "INT_SRC_OVR unexpected reserved flags: 0x%x\n", - p->flags.reserved); + p->inti_flags & + ~(ACPI_MADT_POLARITY_MASK | ACPI_MADT_TRIGGER_MASK)); } break; - case ACPI_MADT_NMI_SRC: + case ACPI_MADT_TYPE_NMI_SOURCE: { - struct acpi_table_nmi_src *p = - (struct acpi_table_nmi_src *)header; + struct acpi_madt_nmi_source *p = + (struct acpi_madt_nmi_source *)header; printk(KERN_INFO PREFIX "NMI_SRC (%s %s global_irq %d)\n", - mps_inti_flags_polarity[p->flags.polarity], - mps_inti_flags_trigger[p->flags.trigger], + mps_inti_flags_polarity[p->inti_flags & ACPI_MADT_POLARITY_MASK], + mps_inti_flags_trigger[(p->inti_flags & ACPI_MADT_TRIGGER_MASK) >> 2], p->global_irq); } break; - case ACPI_MADT_LAPIC_NMI: + case ACPI_MADT_TYPE_LOCAL_APIC_NMI: { - struct acpi_table_lapic_nmi *p = - (struct acpi_table_lapic_nmi *)header; + struct acpi_madt_local_apic_nmi *p = + (struct acpi_madt_local_apic_nmi *)header; printk(KERN_INFO PREFIX "LAPIC_NMI (acpi_id[0x%02x] %s %s lint[0x%x])\n", - p->acpi_id, - mps_inti_flags_polarity[p->flags.polarity], - mps_inti_flags_trigger[p->flags.trigger], + p->processor_id, + mps_inti_flags_polarity[p->inti_flags & ACPI_MADT_POLARITY_MASK ], + mps_inti_flags_trigger[(p->inti_flags & ACPI_MADT_TRIGGER_MASK) >> 2], p->lint); } break; - case ACPI_MADT_LAPIC_ADDR_OVR: + case ACPI_MADT_TYPE_LOCAL_APIC_OVERRIDE: { - struct acpi_table_lapic_addr_ovr *p = - (struct acpi_table_lapic_addr_ovr *)header; + struct acpi_madt_local_apic_override *p = + (struct acpi_madt_local_apic_override *)header; printk(KERN_INFO PREFIX "LAPIC_ADDR_OVR (address[%p])\n", (void *)(unsigned long)p->address); } break; - case ACPI_MADT_IOSAPIC: + case ACPI_MADT_TYPE_IO_SAPIC: { - struct acpi_table_iosapic *p = - (struct acpi_table_iosapic *)header; + struct acpi_madt_io_sapic *p = + (struct acpi_madt_io_sapic *)header; printk(KERN_INFO PREFIX "IOSAPIC (id[0x%x] address[%p] gsi_base[%d])\n", p->id, (void *)(unsigned long)p->address, @@ -134,26 +136,26 @@ void acpi_table_print_madt_entry(acpi_table_entry_header * header) } break; - case ACPI_MADT_LSAPIC: + case ACPI_MADT_TYPE_LOCAL_SAPIC: { - struct acpi_table_lsapic *p = - (struct acpi_table_lsapic *)header; + struct acpi_madt_local_sapic *p = + (struct acpi_madt_local_sapic *)header; printk(KERN_INFO PREFIX "LSAPIC (acpi_id[0x%02x] lsapic_id[0x%02x] lsapic_eid[0x%02x] %s)\n", - p->acpi_id, p->id, p->eid, - p->flags.enabled ? "enabled" : "disabled"); + p->processor_id, p->id, p->eid, + (p->lapic_flags & ACPI_MADT_ENABLED) ? "enabled" : "disabled"); } break; - case ACPI_MADT_PLAT_INT_SRC: + case ACPI_MADT_TYPE_INTERRUPT_SOURCE: { - struct acpi_table_plat_int_src *p = - (struct acpi_table_plat_int_src *)header; + struct acpi_madt_interrupt_source *p = + (struct acpi_madt_interrupt_source *)header; printk(KERN_INFO PREFIX "PLAT_INT_SRC (%s %s type[0x%x] id[0x%04x] eid[0x%x] iosapic_vector[0x%x] global_irq[0x%x]\n", - mps_inti_flags_polarity[p->flags.polarity], - mps_inti_flags_trigger[p->flags.trigger], - p->type, p->id, p->eid, p->iosapic_vector, + mps_inti_flags_polarity[p->inti_flags & ACPI_MADT_POLARITY_MASK], + mps_inti_flags_trigger[(p->inti_flags & ACPI_MADT_TRIGGER_MASK) >> 2], + p->type, p->id, p->eid, p->io_sapic_vector, p->global_irq); } break; @@ -175,7 +177,7 @@ acpi_table_parse_madt_family(char *id, unsigned int max_entries) { struct acpi_table_header *madt = NULL; - acpi_table_entry_header *entry; + struct acpi_subtable_header *entry; unsigned int count = 0; unsigned long madt_end; @@ -183,7 +185,6 @@ acpi_table_parse_madt_family(char *id, return -EINVAL; /* Locate the MADT (if exists). There should only be one. */ - acpi_get_table(id, 0, &madt); if (!madt) { @@ -195,17 +196,17 @@ acpi_table_parse_madt_family(char *id, /* Parse all entries looking for a match. */ - entry = (acpi_table_entry_header *) + entry = (struct acpi_subtable_header *) ((unsigned long)madt + madt_size); - while (((unsigned long)entry) + sizeof(acpi_table_entry_header) < + while (((unsigned long)entry) + sizeof(struct acpi_subtable_header) < madt_end) { if (entry->type == entry_id && (!max_entries || count++ < max_entries)) if (handler(entry, madt_end)) return -EINVAL; - entry = (acpi_table_entry_header *) + entry = (struct acpi_subtable_header *) ((unsigned long)entry + entry->length); } if (max_entries && count > max_entries) { @@ -217,10 +218,10 @@ acpi_table_parse_madt_family(char *id, } int __init -acpi_table_parse_madt(enum acpi_madt_entry_id id, +acpi_table_parse_madt(enum acpi_madt_type id, acpi_madt_entry_handler handler, unsigned int max_entries) { - return acpi_table_parse_madt_family("APIC", + return acpi_table_parse_madt_family(ACPI_SIG_MADT, sizeof(struct acpi_table_madt), id, handler, max_entries); } @@ -228,7 +229,6 @@ acpi_table_parse_madt(enum acpi_madt_entry_id id, int __init acpi_table_parse(char *id, acpi_table_handler handler) { struct acpi_table_header *table = NULL; - if (!handler) return -EINVAL; @@ -245,10 +245,11 @@ int __init acpi_table_parse(char *id, acpi_table_handler handler) * * find RSDP, find and checksum SDT/XSDT. * checksum all tables, print SDT/XSDT - * + * * result: sdt_entry[] is initialized */ + int __init acpi_table_init(void) { acpi_initialize_tables(initial_tables, ACPI_MAX_TABLES, 0); diff --git a/include/linux/acpi.h b/include/linux/acpi.h index 5a2b363..fac7a7b 100644 --- a/include/linux/acpi.h +++ b/include/linux/acpi.h @@ -58,106 +58,6 @@ typedef struct { u8 length; } __attribute__ ((packed)) acpi_table_entry_header; -/* Multiple APIC Description Table (MADT) */ - -enum acpi_madt_entry_id { - ACPI_MADT_LAPIC = 0, - ACPI_MADT_IOAPIC, - ACPI_MADT_INT_SRC_OVR, - ACPI_MADT_NMI_SRC, - ACPI_MADT_LAPIC_NMI, - ACPI_MADT_LAPIC_ADDR_OVR, - ACPI_MADT_IOSAPIC, - ACPI_MADT_LSAPIC, - ACPI_MADT_PLAT_INT_SRC, - ACPI_MADT_ENTRY_COUNT -}; - -typedef struct { - u16 polarity:2; - u16 trigger:2; - u16 reserved:12; -} __attribute__ ((packed)) acpi_interrupt_flags; - -struct acpi_table_lapic { - acpi_table_entry_header header; - u8 acpi_id; - u8 id; - struct { - u32 enabled:1; - u32 reserved:31; - } flags; -} __attribute__ ((packed)); - -struct acpi_table_ioapic { - acpi_table_entry_header header; - u8 id; - u8 reserved; - u32 address; - u32 global_irq_base; -} __attribute__ ((packed)); - -struct acpi_table_int_src_ovr { - acpi_table_entry_header header; - u8 bus; - u8 bus_irq; - u32 global_irq; - acpi_interrupt_flags flags; -} __attribute__ ((packed)); - -struct acpi_table_nmi_src { - acpi_table_entry_header header; - acpi_interrupt_flags flags; - u32 global_irq; -} __attribute__ ((packed)); - -struct acpi_table_lapic_nmi { - acpi_table_entry_header header; - u8 acpi_id; - acpi_interrupt_flags flags; - u8 lint; -} __attribute__ ((packed)); - -struct acpi_table_lapic_addr_ovr { - acpi_table_entry_header header; - u8 reserved[2]; - u64 address; -} __attribute__ ((packed)); - -struct acpi_table_iosapic { - acpi_table_entry_header header; - u8 id; - u8 reserved; - u32 global_irq_base; - u64 address; -} __attribute__ ((packed)); - -struct acpi_table_lsapic { - acpi_table_entry_header header; - u8 acpi_id; - u8 id; - u8 eid; - u8 reserved[3]; - struct { - u32 enabled:1; - u32 reserved:31; - } flags; -} __attribute__ ((packed)); - -struct acpi_table_plat_int_src { - acpi_table_entry_header header; - acpi_interrupt_flags flags; - u8 type; /* See acpi_interrupt_type */ - u8 id; - u8 eid; - u8 iosapic_vector; - u32 global_irq; - struct { - u32 cpei_override_flag:1; - u32 reserved:31; - } plint_flags; -} __attribute__ ((packed)); - enum acpi_interrupt_id { ACPI_INTERRUPT_PMI = 1, ACPI_INTERRUPT_INIT, @@ -285,7 +185,7 @@ typedef int (*acpi_table_handler) (struct acpi_table_header *header); extern acpi_table_handler acpi_table_ops[ACPI_TABLE_COUNT]; -typedef int (*acpi_madt_entry_handler) (acpi_table_entry_header *header, const unsigned long end); +typedef int (*acpi_madt_entry_handler) (struct acpi_subtable_header *header, const unsigned long end); char * __acpi_map_table (unsigned long phys_addr, unsigned long size); unsigned long acpi_find_rsdp (void); @@ -295,11 +195,11 @@ int acpi_numa_init (void); int acpi_table_init (void); int acpi_table_parse (char *id, acpi_table_handler handler); -int acpi_table_parse_madt (enum acpi_madt_entry_id id, acpi_madt_entry_handler handler, unsigned int max_entries); +int acpi_table_parse_madt (enum acpi_madt_type id, acpi_madt_entry_handler handler, unsigned int max_entries); int acpi_table_parse_srat (enum acpi_srat_entry_id id, acpi_madt_entry_handler handler, unsigned int max_entries); int acpi_parse_mcfg (struct acpi_table_header *header); void acpi_table_print (struct acpi_table_header *header, unsigned long phys_addr); -void acpi_table_print_madt_entry (acpi_table_entry_header *madt); +void acpi_table_print_madt_entry (struct acpi_subtable_header *madt); void acpi_table_print_srat_entry (acpi_table_entry_header *srat); /* the following four functions are architecture-dependent */ -- cgit v0.10.2 From 15a58ed12142939d51076380e6e58af477ad96ec Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Remove duplicate table definitions (non-conflicting), cont Signed-off-by: Len Brown diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index 5fafbac..2147511 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -166,7 +166,7 @@ char *__acpi_map_table(unsigned long phys, unsigned long size) #ifdef CONFIG_PCI_MMCONFIG /* The physical address of the MMCONFIG aperture. Set from ACPI tables. */ -struct acpi_table_mcfg_config *pci_mmcfg_config; +struct acpi_mcfg_allocation *pci_mmcfg_config; int pci_mmcfg_config_num; int __init acpi_parse_mcfg(struct acpi_table_header *header) @@ -179,17 +179,13 @@ int __init acpi_parse_mcfg(struct acpi_table_header *header) return -EINVAL; mcfg = (struct acpi_table_mcfg *)header; - if (!mcfg) { - printk(KERN_WARNING PREFIX "Unable to map MCFG\n"); - return -ENODEV; - } /* how many config structures do we have */ pci_mmcfg_config_num = 0; i = header->length - sizeof(struct acpi_table_mcfg); - while (i >= sizeof(struct acpi_table_mcfg_config)) { + while (i >= sizeof(struct acpi_mcfg_allocation)) { ++pci_mmcfg_config_num; - i -= sizeof(struct acpi_table_mcfg_config); + i -= sizeof(struct acpi_mcfg_allocation); }; if (pci_mmcfg_config_num == 0) { printk(KERN_ERR PREFIX "MMCONFIG has no entries\n"); @@ -206,7 +202,7 @@ int __init acpi_parse_mcfg(struct acpi_table_header *header) memcpy(pci_mmcfg_config, &mcfg[1], config_size); for (i = 0; i < pci_mmcfg_config_num; ++i) { - if (pci_mmcfg_config[i].base_reserved) { + if (pci_mmcfg_config[i].address > 0xFFFFFFFF) { printk(KERN_ERR PREFIX "MMCONFIG not in low 4GB of memory\n"); kfree(pci_mmcfg_config); @@ -220,14 +216,14 @@ int __init acpi_parse_mcfg(struct acpi_table_header *header) #endif /* CONFIG_PCI_MMCONFIG */ #ifdef CONFIG_X86_LOCAL_APIC -static int __init acpi_parse_madt(struct acpi_table_header *header) +static int __init acpi_parse_madt(struct acpi_table_header *table) { struct acpi_table_madt *madt = NULL; - if (!header|| !cpu_has_apic) + if (!cpu_has_apic) return -EINVAL; - madt = (struct acpi_table_madt *)header; + madt = (struct acpi_table_madt *)table; if (!madt) { printk(KERN_WARNING PREFIX "Unable to map MADT\n"); return -ENODEV; diff --git a/arch/i386/kernel/acpi/earlyquirk.c b/arch/i386/kernel/acpi/earlyquirk.c index 4261c85..bf86f76 100644 --- a/arch/i386/kernel/acpi/earlyquirk.c +++ b/arch/i386/kernel/acpi/earlyquirk.c @@ -30,7 +30,7 @@ static int __init check_bridge(int vendor, int device) is enabled. */ if (!acpi_use_timer_override && vendor == PCI_VENDOR_ID_NVIDIA) { nvidia_hpet_detected = 0; - acpi_table_parse("HPET", nvidia_hpet_check); + acpi_table_parse(ACPI_SIG_HPET, nvidia_hpet_check); if (nvidia_hpet_detected == 0) { acpi_skip_timer_override = 1; printk(KERN_INFO "Nvidia board " diff --git a/arch/i386/pci/mmconfig.c b/arch/i386/pci/mmconfig.c index 80522e3..5700220 100644 --- a/arch/i386/pci/mmconfig.c +++ b/arch/i386/pci/mmconfig.c @@ -36,7 +36,7 @@ static DECLARE_BITMAP(fallback_slots, MAX_CHECK_BUS*32); static u32 get_base_addr(unsigned int seg, int bus, unsigned devfn) { int cfg_num = -1; - struct acpi_table_mcfg_config *cfg; + struct acpi_mcfg_allocation *cfg; if (seg == 0 && bus < MAX_CHECK_BUS && test_bit(PCI_SLOT(devfn) + 32*bus, fallback_slots)) @@ -48,11 +48,11 @@ static u32 get_base_addr(unsigned int seg, int bus, unsigned devfn) break; } cfg = &pci_mmcfg_config[cfg_num]; - if (cfg->pci_segment_group_number != seg) + if (cfg->pci_segment != seg) continue; if ((cfg->start_bus_number <= bus) && (cfg->end_bus_number >= bus)) - return cfg->base_address; + return cfg->address; } /* Handle more broken MCFG tables on Asus etc. @@ -60,9 +60,9 @@ static u32 get_base_addr(unsigned int seg, int bus, unsigned devfn) this applies to all busses. */ cfg = &pci_mmcfg_config[0]; if (pci_mmcfg_config_num == 1 && - cfg->pci_segment_group_number == 0 && + cfg->pci_segment == 0 && (cfg->start_bus_number | cfg->end_bus_number) == 0) - return cfg->base_address; + return cfg->address; /* Fall back to type 0 */ return 0; @@ -125,7 +125,7 @@ static int pci_mmcfg_write(unsigned int seg, unsigned int bus, unsigned long flags; u32 base; - if ((bus > 255) || (devfn > 255) || (reg > 4095)) + if ((bus > 255) || (devfn > 255) || (reg > 4095)) return -EINVAL; base = get_base_addr(seg, bus, devfn); @@ -199,19 +199,19 @@ void __init pci_mmcfg_init(int type) if ((pci_probe & PCI_PROBE_MMCONF) == 0) return; - acpi_table_parse("MCFG", acpi_parse_mcfg); + acpi_table_parse(ACPI_SIG_MCFG, acpi_parse_mcfg); if ((pci_mmcfg_config_num == 0) || (pci_mmcfg_config == NULL) || - (pci_mmcfg_config[0].base_address == 0)) + (pci_mmcfg_config[0].address == 0)) return; /* Only do this check when type 1 works. If it doesn't work assume we run on a Mac and always use MCFG */ - if (type == 1 && !e820_all_mapped(pci_mmcfg_config[0].base_address, - pci_mmcfg_config[0].base_address + MMCONFIG_APER_MIN, + if (type == 1 && !e820_all_mapped(pci_mmcfg_config[0].address, + pci_mmcfg_config[0].address + MMCONFIG_APER_MIN, E820_RESERVED)) { - printk(KERN_ERR "PCI: BIOS Bug: MCFG area at %x is not E820-reserved\n", - pci_mmcfg_config[0].base_address); + printk(KERN_ERR "PCI: BIOS Bug: MCFG area at %lx is not E820-reserved\n", + (unsigned long)pci_mmcfg_config[0].address); printk(KERN_ERR "PCI: Not using MMCONFIG.\n"); return; } diff --git a/arch/x86_64/kernel/early-quirks.c b/arch/x86_64/kernel/early-quirks.c index 49802f1..bd30d13 100644 --- a/arch/x86_64/kernel/early-quirks.c +++ b/arch/x86_64/kernel/early-quirks.c @@ -32,7 +32,7 @@ static void via_bugs(void) static int nvidia_hpet_detected __initdata; -static int __init nvidia_hpet_check(unsigned long phys, unsigned long size) +static int __init nvidia_hpet_check(struct acpi_table_header *header) { nvidia_hpet_detected = 1; return 0; @@ -53,7 +53,7 @@ static void nvidia_bugs(void) return; nvidia_hpet_detected = 0; - acpi_table_parse(ACPI_HPET, nvidia_hpet_check); + acpi_table_parse(ACPI_SIG_HPET, nvidia_hpet_check); if (nvidia_hpet_detected == 0) { acpi_skip_timer_override = 1; printk(KERN_INFO "Nvidia board " diff --git a/arch/x86_64/mm/srat.c b/arch/x86_64/mm/srat.c index 1087e15..2efe215 100644 --- a/arch/x86_64/mm/srat.c +++ b/arch/x86_64/mm/srat.c @@ -101,7 +101,7 @@ static __init inline int srat_disabled(void) static __init int slit_valid(struct acpi_table_slit *slit) { int i, j; - int d = slit->localities; + int d = slit->locality_count; for (i = 0; i < d; i++) { for (j = 0; j < d; j++) { u8 val = slit->entry[d*i + j]; @@ -127,18 +127,18 @@ void __init acpi_numa_slit_init(struct acpi_table_slit *slit) /* Callback for Proximity Domain -> LAPIC mapping */ void __init -acpi_numa_processor_affinity_init(struct acpi_table_processor_affinity *pa) +acpi_numa_processor_affinity_init(struct acpi_srat_cpu_affinity *pa) { int pxm, node; if (srat_disabled()) return; - if (pa->header.length != sizeof(struct acpi_table_processor_affinity)) { + if (pa->header.length != sizeof(struct acpi_srat_cpu_affinity)) { bad_srat(); return; } - if (pa->flags.enabled == 0) + if ((pa->flags & ACPI_SRAT_CPU_ENABLED) == 0) return; - pxm = pa->proximity_domain; + pxm = pa->proximity_domain_lo; node = setup_node(pxm); if (node < 0) { printk(KERN_ERR "SRAT: Too many proximity domains %x\n", pxm); @@ -254,21 +254,21 @@ static int reserve_hotadd(int node, unsigned long start, unsigned long end) /* Looks good */ if (nd->start == nd->end) { - nd->start = start; - nd->end = end; + nd->start = start; + nd->end = end; changed = 1; - } else { - if (nd->start == end) { - nd->start = start; + } else { + if (nd->start == end) { + nd->start = start; changed = 1; } - if (nd->end == start) { - nd->end = end; + if (nd->end == start) { + nd->end = end; changed = 1; } if (!changed) printk(KERN_ERR "SRAT: Hotplug zone not continuous. Partly ignored\n"); - } + } ret = update_end_of_memory(nd->end); @@ -279,7 +279,7 @@ static int reserve_hotadd(int node, unsigned long start, unsigned long end) /* Callback for parsing of the Proximity Domain <-> Memory Area mappings */ void __init -acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma) +acpi_numa_memory_affinity_init(struct acpi_srat_mem_affinity *ma) { struct bootnode *nd, oldnode; unsigned long start, end; @@ -288,16 +288,17 @@ acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma) if (srat_disabled()) return; - if (ma->header.length != sizeof(struct acpi_table_memory_affinity)) { + if (ma->header.length != sizeof(struct acpi_srat_mem_affinity)) { bad_srat(); return; } - if (ma->flags.enabled == 0) + if ((ma->flags & ACPI_SRAT_MEM_ENABLED) == 0) return; - if (ma->flags.hot_pluggable && !save_add_info()) + + if ((ma->flags & ACPI_SRAT_MEM_HOT_PLUGGABLE) && !save_add_info()) return; - start = ma->base_addr_lo | ((u64)ma->base_addr_hi << 32); - end = start + (ma->length_lo | ((u64)ma->length_hi << 32)); + start = ma->base_address; + end = start + ma->length; pxm = ma->proximity_domain; node = setup_node(pxm); if (node < 0) { @@ -337,7 +338,8 @@ acpi_numa_memory_affinity_init(struct acpi_table_memory_affinity *ma) push_node_boundaries(node, nd->start >> PAGE_SHIFT, nd->end >> PAGE_SHIFT); - if (ma->flags.hot_pluggable && (reserve_hotadd(node, start, end) < 0)) { + if ((ma->flags & ACPI_SRAT_MEM_HOT_PLUGGABLE) && + (reserve_hotadd(node, start, end) < 0)) { /* Ignore hotadd region. Undo damage */ printk(KERN_NOTICE "SRAT: Hotplug region ignored\n"); *nd = oldnode; @@ -394,7 +396,7 @@ int __init acpi_scan_nodes(unsigned long start, unsigned long end) /* First clean up the node list */ for (i = 0; i < MAX_NUMNODES; i++) { - cutoff_node(i, start, end); + cutoff_node(i, start, end); if ((nodes[i].end - nodes[i].start) < NODE_MIN_SIZE) { unparse_node(i); node_set_offline(i); @@ -426,7 +428,7 @@ int __init acpi_scan_nodes(unsigned long start, unsigned long end) if (!node_online(i)) setup_node_bootmem(i, nodes[i].start, nodes[i].end); - for (i = 0; i < NR_CPUS; i++) { + for (i = 0; i < NR_CPUS; i++) { if (cpu_to_node[i] == NUMA_NO_NODE) continue; if (!node_isset(cpu_to_node[i], nodes_parsed)) @@ -461,7 +463,7 @@ int __node_distance(int a, int b) if (!acpi_slit) return a == b ? 10 : 20; - index = acpi_slit->localities * node_to_pxm(a); + index = acpi_slit->locality_count * node_to_pxm(a); return acpi_slit->entry[index + node_to_pxm(b)]; } diff --git a/arch/x86_64/pci/mmconfig.c b/arch/x86_64/pci/mmconfig.c index f8b6b28..faabb6e 100644 --- a/arch/x86_64/pci/mmconfig.c +++ b/arch/x86_64/pci/mmconfig.c @@ -1,6 +1,6 @@ /* * mmconfig.c - Low-level direct PCI config space access via MMCONFIG - * + * * This is an 64bit optimized version that always keeps the full mmconfig * space mapped. This allows lockless config space operation. */ @@ -25,7 +25,7 @@ static DECLARE_BITMAP(fallback_slots, 32*MAX_CHECK_BUS); /* Static virtual mapping of the MMCONFIG aperture */ struct mmcfg_virt { - struct acpi_table_mcfg_config *cfg; + struct acpi_mcfg_allocation *cfg; char __iomem *virt; }; static struct mmcfg_virt *pci_mmcfg_virt; @@ -33,14 +33,14 @@ static struct mmcfg_virt *pci_mmcfg_virt; static char __iomem *get_virt(unsigned int seg, unsigned bus) { int cfg_num = -1; - struct acpi_table_mcfg_config *cfg; + struct acpi_mcfg_allocation *cfg; while (1) { ++cfg_num; if (cfg_num >= pci_mmcfg_config_num) break; cfg = pci_mmcfg_virt[cfg_num].cfg; - if (cfg->pci_segment_group_number != seg) + if (cfg->pci_segment != seg) continue; if ((cfg->start_bus_number <= bus) && (cfg->end_bus_number >= bus)) @@ -52,7 +52,7 @@ static char __iomem *get_virt(unsigned int seg, unsigned bus) this applies to all busses. */ cfg = &pci_mmcfg_config[0]; if (pci_mmcfg_config_num == 1 && - cfg->pci_segment_group_number == 0 && + cfg->pci_segment == 0 && (cfg->start_bus_number | cfg->end_bus_number) == 0) return pci_mmcfg_virt[0].virt; @@ -170,19 +170,19 @@ void __init pci_mmcfg_init(int type) if ((pci_probe & PCI_PROBE_MMCONF) == 0) return; - acpi_table_parse(ACPI_MCFG, acpi_parse_mcfg); + acpi_table_parse(ACPI_SIG_MCFG, acpi_parse_mcfg); if ((pci_mmcfg_config_num == 0) || (pci_mmcfg_config == NULL) || - (pci_mmcfg_config[0].base_address == 0)) + (pci_mmcfg_config[0].address == 0)) return; /* Only do this check when type 1 works. If it doesn't work assume we run on a Mac and always use MCFG */ - if (type == 1 && !e820_all_mapped(pci_mmcfg_config[0].base_address, - pci_mmcfg_config[0].base_address + MMCONFIG_APER_MIN, + if (type == 1 && !e820_all_mapped(pci_mmcfg_config[0].address, + pci_mmcfg_config[0].address + MMCONFIG_APER_MIN, E820_RESERVED)) { - printk(KERN_ERR "PCI: BIOS Bug: MCFG area at %x is not E820-reserved\n", - pci_mmcfg_config[0].base_address); + printk(KERN_ERR "PCI: BIOS Bug: MCFG area at %lx is not E820-reserved\n", + (unsigned long)pci_mmcfg_config[0].address); printk(KERN_ERR "PCI: Not using MMCONFIG.\n"); return; } @@ -194,15 +194,16 @@ void __init pci_mmcfg_init(int type) } for (i = 0; i < pci_mmcfg_config_num; ++i) { pci_mmcfg_virt[i].cfg = &pci_mmcfg_config[i]; - pci_mmcfg_virt[i].virt = ioremap_nocache(pci_mmcfg_config[i].base_address, + pci_mmcfg_virt[i].virt = ioremap_nocache(pci_mmcfg_config[i].address, MMCONFIG_APER_MAX); if (!pci_mmcfg_virt[i].virt) { printk(KERN_ERR "PCI: Cannot map mmconfig aperture for " "segment %d\n", - pci_mmcfg_config[i].pci_segment_group_number); + pci_mmcfg_config[i].pci_segment); return; } - printk(KERN_INFO "PCI: Using MMCONFIG at %x\n", pci_mmcfg_config[i].base_address); + printk(KERN_INFO "PCI: Using MMCONFIG at %lx\n", + (unsigned long)pci_mmcfg_config[i].address); } unreachable_devices(); diff --git a/drivers/acpi/blacklist.c b/drivers/acpi/blacklist.c index bdc169b..c8f4cac 100644 --- a/drivers/acpi/blacklist.c +++ b/drivers/acpi/blacklist.c @@ -79,7 +79,7 @@ static int __init blacklist_by_year(void) { int year = dmi_get_year(DMI_BIOS_DATE); /* Doesn't exist? Likely an old system */ - if (year == -1) + if (year == -1) return 1; /* 0? Likely a buggy new BIOS */ if (year == 0) diff --git a/drivers/acpi/ec.c b/drivers/acpi/ec.c index 710364e..743ce27 100644 --- a/drivers/acpi/ec.c +++ b/drivers/acpi/ec.c @@ -872,7 +872,8 @@ static int __init acpi_ec_get_real_ecdt(void) acpi_status status; struct acpi_table_ecdt *ecdt_ptr; - status = acpi_get_table("ECDT", 1, (struct acpi_table_header **)&ecdt_ptr); + status = acpi_get_table(ACPI_SIG_ECDT, 1, + (struct acpi_table_header **)&ecdt_ptr); if (ACPI_FAILURE(status)) return -ENODEV; diff --git a/drivers/acpi/numa.c b/drivers/acpi/numa.c index bd96a70..4a9faff 100644 --- a/drivers/acpi/numa.c +++ b/drivers/acpi/numa.c @@ -45,7 +45,7 @@ int __cpuinitdata pxm_to_node_map[MAX_PXM_DOMAINS] int __cpuinitdata node_to_pxm_map[MAX_NUMNODES] = { [0 ... MAX_NUMNODES - 1] = PXM_INVAL }; -extern int __init acpi_table_parse_madt_family(enum acpi_table_id id, +extern int __init acpi_table_parse_madt_family(char *id, unsigned long madt_size, int entry_id, acpi_madt_entry_handler handler, @@ -89,7 +89,7 @@ void __cpuinit acpi_unmap_pxm_to_node(int node) node_clear(node, nodes_found_map); } -void __init acpi_table_print_srat_entry(acpi_table_entry_header * header) +void __init acpi_table_print_srat_entry(struct acpi_subtable_header * header) { ACPI_FUNCTION_NAME("acpi_table_print_srat_entry"); @@ -99,36 +99,35 @@ void __init acpi_table_print_srat_entry(acpi_table_entry_header * header) switch (header->type) { - case ACPI_SRAT_PROCESSOR_AFFINITY: + case ACPI_SRAT_TYPE_CPU_AFFINITY: #ifdef ACPI_DEBUG_OUTPUT { - struct acpi_table_processor_affinity *p = - (struct acpi_table_processor_affinity *)header; + struct acpi_srat_cpu_affinity *p = + (struct acpi_srat_cpu_affinity *)header; ACPI_DEBUG_PRINT((ACPI_DB_INFO, "SRAT Processor (id[0x%02x] eid[0x%02x]) in proximity domain %d %s\n", - p->apic_id, p->lsapic_eid, - p->proximity_domain, - p->flags. - enabled ? "enabled" : "disabled")); + p->apic_id, p->local_sapic_eid, + p->proximity_domain_lo, + (p->flags & ACPI_SRAT_CPU_ENABLED)? + "enabled" : "disabled")); } #endif /* ACPI_DEBUG_OUTPUT */ break; - case ACPI_SRAT_MEMORY_AFFINITY: + case ACPI_SRAT_TYPE_MEMORY_AFFINITY: #ifdef ACPI_DEBUG_OUTPUT { - struct acpi_table_memory_affinity *p = - (struct acpi_table_memory_affinity *)header; + struct acpi_srat_mem_affinity *p = + (struct acpi_srat_mem_affinity *)header; ACPI_DEBUG_PRINT((ACPI_DB_INFO, - "SRAT Memory (0x%08x%08x length 0x%08x%08x type 0x%x) in proximity domain %d %s%s\n", - p->base_addr_hi, p->base_addr_lo, - p->length_hi, p->length_lo, + "SRAT Memory (0x%lx length 0x%lx type 0x%x) in proximity domain %d %s%s\n", + (unsigned long)p->base_address, + (unsigned long)p->length, p->memory_type, p->proximity_domain, - p->flags. - enabled ? "enabled" : "disabled", - p->flags. - hot_pluggable ? " hot-pluggable" : - "")); + (p->flags & ACPI_SRAT_MEM_ENABLED)? + "enabled" : "disabled", + (p->flags & ACPI_SRAT_MEM_HOT_PLUGGABLE)? + " hot-pluggable" : "")); } #endif /* ACPI_DEBUG_OUTPUT */ break; @@ -141,18 +140,18 @@ void __init acpi_table_print_srat_entry(acpi_table_entry_header * header) } } -static int __init acpi_parse_slit(unsigned long phys_addr, unsigned long size) +static int __init acpi_parse_slit(struct acpi_table_header *table) { struct acpi_table_slit *slit; u32 localities; - if (!phys_addr || !size) + if (!table) return -EINVAL; - slit = (struct acpi_table_slit *)__va(phys_addr); + slit = (struct acpi_table_slit *)table; /* downcast just for %llu vs %lu for i386/ia64 */ - localities = (u32) slit->localities; + localities = (u32) slit->locality_count; acpi_numa_slit_init(slit); @@ -160,12 +159,12 @@ static int __init acpi_parse_slit(unsigned long phys_addr, unsigned long size) } static int __init -acpi_parse_processor_affinity(acpi_table_entry_header * header, +acpi_parse_processor_affinity(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_processor_affinity *processor_affinity; + struct acpi_srat_cpu_affinity *processor_affinity; - processor_affinity = (struct acpi_table_processor_affinity *)header; + processor_affinity = (struct acpi_srat_cpu_affinity *)header; if (!processor_affinity) return -EINVAL; @@ -178,12 +177,12 @@ acpi_parse_processor_affinity(acpi_table_entry_header * header, } static int __init -acpi_parse_memory_affinity(acpi_table_entry_header * header, +acpi_parse_memory_affinity(struct acpi_subtable_header * header, const unsigned long end) { - struct acpi_table_memory_affinity *memory_affinity; + struct acpi_srat_mem_affinity *memory_affinity; - memory_affinity = (struct acpi_table_memory_affinity *)header; + memory_affinity = (struct acpi_srat_mem_affinity *)header; if (!memory_affinity) return -EINVAL; @@ -195,23 +194,23 @@ acpi_parse_memory_affinity(acpi_table_entry_header * header, return 0; } -static int __init acpi_parse_srat(unsigned long phys_addr, unsigned long size) +static int __init acpi_parse_srat(struct acpi_table_header *table) { struct acpi_table_srat *srat; - if (!phys_addr || !size) + if (!table) return -EINVAL; - srat = (struct acpi_table_srat *)__va(phys_addr); + srat = (struct acpi_table_srat *)table; return 0; } int __init -acpi_table_parse_srat(enum acpi_srat_entry_id id, +acpi_table_parse_srat(enum acpi_srat_type id, acpi_madt_entry_handler handler, unsigned int max_entries) { - return acpi_table_parse_madt_family(ACPI_SRAT, + return acpi_table_parse_madt_family(ACPI_SIG_SRAT, sizeof(struct acpi_table_srat), id, handler, max_entries); } @@ -221,17 +220,17 @@ int __init acpi_numa_init(void) int result; /* SRAT: Static Resource Affinity Table */ - result = acpi_table_parse(ACPI_SRAT, acpi_parse_srat); + result = acpi_table_parse(ACPI_SIG_SRAT, acpi_parse_srat); if (result > 0) { - result = acpi_table_parse_srat(ACPI_SRAT_PROCESSOR_AFFINITY, + result = acpi_table_parse_srat(ACPI_SRAT_TYPE_CPU_AFFINITY, acpi_parse_processor_affinity, NR_CPUS); - result = acpi_table_parse_srat(ACPI_SRAT_MEMORY_AFFINITY, acpi_parse_memory_affinity, NR_NODE_MEMBLKS); // IA64 specific + result = acpi_table_parse_srat(ACPI_SRAT_TYPE_MEMORY_AFFINITY, acpi_parse_memory_affinity, NR_NODE_MEMBLKS); // IA64 specific } /* SLIT: System Locality Information Table */ - result = acpi_table_parse(ACPI_SLIT, acpi_parse_slit); + result = acpi_table_parse(ACPI_SIG_SLIT, acpi_parse_slit); acpi_numa_arch_fixup(); return 0; diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c index f1afd26..a7b33d2 100644 --- a/drivers/char/ipmi/ipmi_si_intf.c +++ b/drivers/char/ipmi/ipmi_si_intf.c @@ -1802,7 +1802,7 @@ static __devinit int try_init_acpi(struct SPMITable *spmi) return -ENODEV; } - if (spmi->addr.address_space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) + if (spmi->addr.space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) addr_space = IPMI_MEM_ADDR_SPACE; else addr_space = IPMI_IO_ADDR_SPACE; @@ -1848,19 +1848,19 @@ static __devinit int try_init_acpi(struct SPMITable *spmi) info->irq_setup = NULL; } - if (spmi->addr.register_bit_width) { + if (spmi->addr.bit_width) { /* A (hopefully) properly formed register bit width. */ - info->io.regspacing = spmi->addr.register_bit_width / 8; + info->io.regspacing = spmi->addr.bit_width / 8; } else { info->io.regspacing = DEFAULT_REGSPACING; } info->io.regsize = info->io.regspacing; - info->io.regshift = spmi->addr.register_bit_offset; + info->io.regshift = spmi->addr.bit_offset; - if (spmi->addr.address_space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) { + if (spmi->addr.space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY) { info->io_setup = mem_setup; info->io.addr_type = IPMI_IO_ADDR_SPACE; - } else if (spmi->addr.address_space_id == ACPI_ADR_SPACE_SYSTEM_IO) { + } else if (spmi->addr.space_id == ACPI_ADR_SPACE_SYSTEM_IO) { info->io_setup = port_setup; info->io.addr_type = IPMI_MEM_ADDR_SPACE; } else { @@ -1888,10 +1888,8 @@ static __devinit void acpi_find_bmc(void) return; for (i = 0; ; i++) { - status = acpi_get_firmware_table("SPMI", i+1, - ACPI_LOGICAL_ADDRESSING, - (struct acpi_table_header **) - &spmi); + status = acpi_get_table(ACPI_SIG_SPMI, i+1, + (struct acpi_table_header **)&spmi); if (status != AE_OK) return; diff --git a/drivers/char/tpm/tpm_bios.c b/drivers/char/tpm/tpm_bios.c index a611972..7fca5f4 100644 --- a/drivers/char/tpm/tpm_bios.c +++ b/drivers/char/tpm/tpm_bios.c @@ -372,10 +372,8 @@ static int read_log(struct tpm_bios_log *log) } /* Find TCPA entry in RSDT (ACPI_LOGICAL_ADDRESSING) */ - status = acpi_get_firmware_table(ACPI_TCPA_SIG, 1, - ACPI_LOGICAL_ADDRESSING, - (struct acpi_table_header **) - &buff); + status = acpi_get_table(ACPI_SIG_TCPA, 1, + (struct acpi_table_header **)&buff); if (ACPI_FAILURE(status)) { printk(KERN_ERR "%s: ERROR - Could not get TCPA table\n", @@ -409,7 +407,7 @@ static int read_log(struct tpm_bios_log *log) log->bios_event_log_end = log->bios_event_log + len; - acpi_os_map_memory(start, len, (void *) &virt); + virt = acpi_os_map_memory(start, len); memcpy(log->bios_event_log, virt, len); diff --git a/drivers/firmware/pcdp.c b/drivers/firmware/pcdp.c index c2ad72f..2b4b76e 100644 --- a/drivers/firmware/pcdp.c +++ b/drivers/firmware/pcdp.c @@ -26,7 +26,7 @@ setup_serial_console(struct pcdp_uart *uart) static char options[64], *p = options; char parity; - mmio = (uart->addr.address_space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY); + mmio = (uart->addr.space_id == ACPI_ADR_SPACE_SYSTEM_MEMORY); p += sprintf(p, "console=uart,%s,0x%lx", mmio ? "mmio" : "io", uart->addr.address); if (uart->baud) { diff --git a/drivers/pci/hotplug/acpiphp_glue.c b/drivers/pci/hotplug/acpiphp_glue.c index bd1faeb..fca978f 100644 --- a/drivers/pci/hotplug/acpiphp_glue.c +++ b/drivers/pci/hotplug/acpiphp_glue.c @@ -773,13 +773,13 @@ static int get_gsi_base(acpi_handle handle, u32 *gsi_base) goto out; table = obj->buffer.pointer; - switch (((acpi_table_entry_header *)table)->type) { - case ACPI_MADT_IOSAPIC: - *gsi_base = ((struct acpi_table_iosapic *)table)->global_irq_base; + switch (((struct acpi_subtable_header *)table)->type) { + case ACPI_MADT_TYPE_IO_SAPIC: + *gsi_base = ((struct acpi_madt_io_sapic *)table)->global_irq_base; result = 0; break; - case ACPI_MADT_IOAPIC: - *gsi_base = ((struct acpi_table_ioapic *)table)->global_irq_base; + case ACPI_MADT_TYPE_IO_APIC: + *gsi_base = ((struct acpi_madt_io_apic *)table)->global_irq_base; result = 0; break; default: diff --git a/include/asm-i386/mach-es7000/mach_mpparse.h b/include/asm-i386/mach-es7000/mach_mpparse.h index 99f66be..24990e5 100644 --- a/include/asm-i386/mach-es7000/mach_mpparse.h +++ b/include/asm-i386/mach-es7000/mach_mpparse.h @@ -3,13 +3,13 @@ #include -static inline void mpc_oem_bus_info(struct mpc_config_bus *m, char *name, +static inline void mpc_oem_bus_info(struct mpc_config_bus *m, char *name, struct mpc_config_translation *translation) { Dprintk("Bus #%d is %s\n", m->mpc_busid, name); } -static inline void mpc_oem_pci_bus(struct mpc_config_bus *m, +static inline void mpc_oem_pci_bus(struct mpc_config_bus *m, struct mpc_config_translation *translation) { } @@ -22,7 +22,7 @@ static inline int mps_oem_check(struct mp_config_table *mpc, char *oem, char *productid) { if (mpc->mpc_oemptr) { - struct mp_config_oemtable *oem_table = + struct mp_config_oemtable *oem_table = (struct mp_config_oemtable *)mpc->mpc_oemptr; if (!strncmp(oem, "UNISYS", 6)) return parse_unisys_oem((char *)oem_table); @@ -31,12 +31,13 @@ static inline int mps_oem_check(struct mp_config_table *mpc, char *oem, } #ifdef CONFIG_ACPI + static inline int es7000_check_dsdt(void) { - struct acpi_table_header *header = NULL; - if(!acpi_get_table_header_early(ACPI_DSDT, &header)) - acpi_table_print(header, 0); - if (!strncmp(header->oem_id, "UNISYS", 6)) + struct acpi_table_header header; + memcpy(&header, 0, sizeof(struct acpi_table_header)); + acpi_get_table_header(ACPI_SIG_DSDT, 0, &header); + if (!strncmp(header.oem_id, "UNISYS", 6)) return 1; return 0; } @@ -44,7 +45,7 @@ static inline int es7000_check_dsdt(void) /* Hook from generic ACPI tables.c */ static inline int acpi_madt_oem_check(char *oem_id, char *oem_table_id) { - unsigned long oem_addr; + unsigned long oem_addr; if (!find_unisys_acpi_oem_table(&oem_addr)) { if (es7000_check_dsdt()) return parse_unisys_oem((char *)oem_addr); diff --git a/include/linux/acpi.h b/include/linux/acpi.h index fac7a7b..815f1fb 100644 --- a/include/linux/acpi.h +++ b/include/linux/acpi.h @@ -53,11 +53,6 @@ enum acpi_irq_model_id { extern enum acpi_irq_model_id acpi_irq_model; -typedef struct { - u8 type; - u8 length; -} __attribute__ ((packed)) acpi_table_entry_header; - enum acpi_interrupt_id { ACPI_INTERRUPT_PMI = 1, ACPI_INTERRUPT_INIT, @@ -67,74 +62,6 @@ enum acpi_interrupt_id { #define ACPI_SPACE_MEM 0 -struct acpi_gen_regaddr { - u8 space_id; - u8 bit_width; - u8 bit_offset; - u8 resv; - u32 addrl; - u32 addrh; -} __attribute__ ((packed)); - -/* - * Simple Boot Flags - * http://www.microsoft.com/whdc/hwdev/resources/specs/simp_bios.mspx - */ -struct acpi_table_sbf -{ - u8 sbf_signature[4]; - u32 sbf_len; - u8 sbf_revision; - u8 sbf_csum; - u8 sbf_oemid[6]; - u8 sbf_oemtable[8]; - u8 sbf_revdata[4]; - u8 sbf_creator[4]; - u8 sbf_crearev[4]; - u8 sbf_cmos; - u8 sbf_spare[3]; -} __attribute__ ((packed)); - -/* - * System Resource Affinity Table (SRAT) - * http://www.microsoft.com/whdc/hwdev/platform/proc/SRAT.mspx - */ - -enum acpi_srat_entry_id { - ACPI_SRAT_PROCESSOR_AFFINITY = 0, - ACPI_SRAT_MEMORY_AFFINITY, - ACPI_SRAT_ENTRY_COUNT -}; - -struct acpi_table_processor_affinity { - acpi_table_entry_header header; - u8 proximity_domain; - u8 apic_id; - struct { - u32 enabled:1; - u32 reserved:31; - } flags; - u8 lsapic_eid; - u8 reserved[7]; -} __attribute__ ((packed)); - -struct acpi_table_memory_affinity { - acpi_table_entry_header header; - u8 proximity_domain; - u8 reserved1[5]; - u32 base_addr_lo; - u32 base_addr_hi; - u32 length_lo; - u32 length_hi; - u32 memory_type; /* See acpi_address_range_id */ - struct { - u32 enabled:1; - u32 hot_pluggable:1; - u32 reserved:30; - } flags; - u64 reserved2; -} __attribute__ ((packed)); - enum acpi_address_range_id { ACPI_ADDRESS_RANGE_MEMORY = 1, ACPI_ADDRESS_RANGE_RESERVED = 2, @@ -144,46 +71,9 @@ enum acpi_address_range_id { }; -/* PCI MMCONFIG */ - -/* Defined in PCI Firmware Specification 3.0 */ -struct acpi_table_mcfg_config { - u32 base_address; - u32 base_reserved; - u16 pci_segment_group_number; - u8 start_bus_number; - u8 end_bus_number; - u8 reserved[4]; -} __attribute__ ((packed)); - /* Table Handlers */ -enum acpi_table_id { - ACPI_TABLE_UNKNOWN = 0, - ACPI_APIC, - ACPI_BOOT, - ACPI_DBGP, - ACPI_DSDT, - ACPI_ECDT, - ACPI_ETDT, - ACPI_FADT, - ACPI_FACS, - ACPI_OEMX, - ACPI_PSDT, - ACPI_SBST, - ACPI_SLIT, - ACPI_SPCR, - ACPI_SRAT, - ACPI_SSDT, - ACPI_SPMI, - ACPI_HPET, - ACPI_MCFG, - ACPI_TABLE_COUNT -}; - -typedef int (*acpi_table_handler) (struct acpi_table_header *header); - -extern acpi_table_handler acpi_table_ops[ACPI_TABLE_COUNT]; +typedef int (*acpi_table_handler) (struct acpi_table_header *table); typedef int (*acpi_madt_entry_handler) (struct acpi_subtable_header *header, const unsigned long end); @@ -196,11 +86,10 @@ int acpi_numa_init (void); int acpi_table_init (void); int acpi_table_parse (char *id, acpi_table_handler handler); int acpi_table_parse_madt (enum acpi_madt_type id, acpi_madt_entry_handler handler, unsigned int max_entries); -int acpi_table_parse_srat (enum acpi_srat_entry_id id, acpi_madt_entry_handler handler, unsigned int max_entries); +int acpi_table_parse_srat (enum acpi_srat_type id, acpi_madt_entry_handler handler, unsigned int max_entries); int acpi_parse_mcfg (struct acpi_table_header *header); -void acpi_table_print (struct acpi_table_header *header, unsigned long phys_addr); void acpi_table_print_madt_entry (struct acpi_subtable_header *madt); -void acpi_table_print_srat_entry (acpi_table_entry_header *srat); +void acpi_table_print_srat_entry (struct acpi_subtable_header *srat); /* the following four functions are architecture-dependent */ #ifdef CONFIG_HAVE_ARCH_PARSE_SRAT @@ -211,8 +100,8 @@ void acpi_table_print_srat_entry (acpi_table_entry_header *srat); #define acpi_numa_arch_fixup() do {} while (0) #else void acpi_numa_slit_init (struct acpi_table_slit *slit); -void acpi_numa_processor_affinity_init (struct acpi_table_processor_affinity *pa); -void acpi_numa_memory_affinity_init (struct acpi_table_memory_affinity *ma); +void acpi_numa_processor_affinity_init (struct acpi_srat_cpu_affinity *pa); +void acpi_numa_memory_affinity_init (struct acpi_srat_mem_affinity *ma); void acpi_numa_arch_fixup(void); #endif @@ -227,7 +116,7 @@ int acpi_unregister_ioapic(acpi_handle handle, u32 gsi_base); extern int acpi_mp_config; -extern struct acpi_table_mcfg_config *pci_mmcfg_config; +extern struct acpi_mcfg_allocation *pci_mmcfg_config; extern int pci_mmcfg_config_num; extern int sbf_port; -- cgit v0.10.2 From 77f6a9fca39f4f19d2d9d5fff1ff5c2ccf20629c Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Update debug output routines for data structure changes Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/executer/exdump.c b/drivers/acpi/executer/exdump.c index 2450943..c9cab16 100644 --- a/drivers/acpi/executer/exdump.c +++ b/drivers/acpi/executer/exdump.c @@ -59,8 +59,6 @@ static void acpi_ex_out_string(char *title, char *value); static void acpi_ex_out_pointer(char *title, void *value); -static void acpi_ex_out_address(char *title, acpi_physical_address value); - static void acpi_ex_dump_object(union acpi_operand_object *obj_desc, struct acpi_exdump_info *info); @@ -92,10 +90,11 @@ static struct acpi_exdump_info acpi_ex_dump_string[4] = { {ACPI_EXD_STRING, 0, NULL} }; -static struct acpi_exdump_info acpi_ex_dump_buffer[4] = { +static struct acpi_exdump_info acpi_ex_dump_buffer[5] = { {ACPI_EXD_INIT, ACPI_EXD_TABLE_SIZE(acpi_ex_dump_buffer), NULL}, {ACPI_EXD_UINT32, ACPI_EXD_OFFSET(buffer.length), "Length"}, {ACPI_EXD_POINTER, ACPI_EXD_OFFSET(buffer.pointer), "Pointer"}, + {ACPI_EXD_POINTER, ACPI_EXD_OFFSET(buffer.node), "Parent Node"}, {ACPI_EXD_BUFFER, 0, NULL} }; @@ -165,8 +164,8 @@ static struct acpi_exdump_info acpi_ex_dump_power[5] = { static struct acpi_exdump_info acpi_ex_dump_processor[7] = { {ACPI_EXD_INIT, ACPI_EXD_TABLE_SIZE(acpi_ex_dump_processor), NULL}, - {ACPI_EXD_UINT32, ACPI_EXD_OFFSET(processor.proc_id), "Processor ID"}, - {ACPI_EXD_UINT32, ACPI_EXD_OFFSET(processor.length), "Length"}, + {ACPI_EXD_UINT8, ACPI_EXD_OFFSET(processor.proc_id), "Processor ID"}, + {ACPI_EXD_UINT8, ACPI_EXD_OFFSET(processor.length), "Length"}, {ACPI_EXD_ADDRESS, ACPI_EXD_OFFSET(processor.address), "Address"}, {ACPI_EXD_POINTER, ACPI_EXD_OFFSET(processor.system_notify), "System Notify"}, @@ -379,18 +378,12 @@ acpi_ex_dump_object(union acpi_operand_object *obj_desc, break; case ACPI_EXD_POINTER: + case ACPI_EXD_ADDRESS: acpi_ex_out_pointer(name, *ACPI_CAST_PTR(void *, target)); break; - case ACPI_EXD_ADDRESS: - - acpi_ex_out_address(name, - *ACPI_CAST_PTR - (acpi_physical_address, target)); - break; - case ACPI_EXD_STRING: acpi_ut_print_string(obj_desc->string.pointer, @@ -834,16 +827,6 @@ static void acpi_ex_out_pointer(char *title, void *value) acpi_os_printf("%20s : %p\n", title, value); } -static void acpi_ex_out_address(char *title, acpi_physical_address value) -{ - -#if ACPI_MACHINE_WIDTH == 16 - acpi_os_printf("%20s : %p\n", title, value); -#else - acpi_os_printf("%20s : %8.8X%8.8X\n", title, ACPI_FORMAT_UINT64(value)); -#endif -} - /******************************************************************************* * * FUNCTION: acpi_ex_dump_namespace_node -- cgit v0.10.2 From 428f211297bc95fd41f23830eab4180339020dd0 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Miscellaneous table manager updates and optimizations Signed-off-by: Bob Moore Signed-off-by: Len Brown diff --git a/drivers/acpi/blacklist.c b/drivers/acpi/blacklist.c index c8f4cac..f289fd4 100644 --- a/drivers/acpi/blacklist.c +++ b/drivers/acpi/blacklist.c @@ -103,7 +103,7 @@ int __init acpi_blacklisted(void) { int i = 0; int blacklisted = 0; - struct acpi_table_header *table_header; + struct acpi_table_header table_header; while (acpi_blacklist[i].oem_id[0] != '\0') { if (acpi_get_table_header(acpi_blacklist[i].table, 0, &table_header)) { @@ -111,13 +111,13 @@ int __init acpi_blacklisted(void) continue; } - if (strncmp(acpi_blacklist[i].oem_id, table_header->oem_id, 6)) { + if (strncmp(acpi_blacklist[i].oem_id, table_header.oem_id, 6)) { i++; continue; } if (strncmp - (acpi_blacklist[i].oem_table_id, table_header->oem_table_id, + (acpi_blacklist[i].oem_table_id, table_header.oem_table_id, 8)) { i++; continue; @@ -126,14 +126,14 @@ int __init acpi_blacklisted(void) if ((acpi_blacklist[i].oem_revision_predicate == all_versions) || (acpi_blacklist[i].oem_revision_predicate == less_than_or_equal - && table_header->oem_revision <= + && table_header.oem_revision <= acpi_blacklist[i].oem_revision) || (acpi_blacklist[i].oem_revision_predicate == greater_than_or_equal - && table_header->oem_revision >= + && table_header.oem_revision >= acpi_blacklist[i].oem_revision) || (acpi_blacklist[i].oem_revision_predicate == equal - && table_header->oem_revision == + && table_header.oem_revision == acpi_blacklist[i].oem_revision)) { printk(KERN_ERR PREFIX diff --git a/drivers/acpi/executer/exconfig.c b/drivers/acpi/executer/exconfig.c index 20a5ab8..7aa18f9 100644 --- a/drivers/acpi/executer/exconfig.c +++ b/drivers/acpi/executer/exconfig.c @@ -279,13 +279,14 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, acpi_native_uint table_index; acpi_physical_address address; struct acpi_table_header table_header; + struct acpi_table_desc table_desc; acpi_integer temp; u32 i; ACPI_FUNCTION_TRACE(ex_load_op); /* Object can be either an op_region or a Field */ - + ACPI_MEMSET(&table_desc, 0, sizeof(struct acpi_table_desc)); switch (ACPI_GET_OBJECT_TYPE(obj_desc)) { case ACPI_TYPE_REGION: @@ -408,10 +409,13 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, goto cleanup; } + table_desc.pointer = table_ptr; + table_desc.length = table_ptr->length; + table_desc.flags = ACPI_TABLE_ORIGIN_ALLOCATED; /* * Install the new table into the local data structures */ - status = acpi_tb_add_table(table_ptr, &table_index); + status = acpi_tb_add_table(&table_desc, &table_index); if (ACPI_FAILURE(status)) { goto cleanup; } diff --git a/drivers/acpi/tables/tbinstal.c b/drivers/acpi/tables/tbinstal.c index 9e0b3ce..b07d9c8 100644 --- a/drivers/acpi/tables/tbinstal.c +++ b/drivers/acpi/tables/tbinstal.c @@ -61,16 +61,19 @@ ACPI_MODULE_NAME("tbinstal") *****************************************************************************/ acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc) { - acpi_status status; + acpi_status status = AE_OK; ACPI_FUNCTION_TRACE(tb_verify_table); /* Map the table if necessary */ if (!table_desc->pointer) { - table_desc->pointer = - acpi_tb_map(table_desc->address, table_desc->length, - table_desc->flags & ACPI_TABLE_ORIGIN_MASK); + if ((table_desc->flags & ACPI_TABLE_ORIGIN_MASK) == + ACPI_TABLE_ORIGIN_MAPPED) { + table_desc->pointer = + acpi_os_map_memory(table_desc->address, + table_desc->length); + } if (!table_desc->pointer) { return_ACPI_STATUS(AE_NO_MEMORY); } @@ -78,14 +81,15 @@ acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc) /* FACS is the odd table, has no standard ACPI header and no checksum */ - if (ACPI_COMPARE_NAME(&(table_desc->signature), ACPI_SIG_FACS)) { - return_ACPI_STATUS(AE_OK); - } + if (!ACPI_COMPARE_NAME(&table_desc->signature, ACPI_SIG_FACS)) { - /* Always calculate checksum, ignore bad checksum if requested */ + /* Always calculate checksum, ignore bad checksum if requested */ + + status = + acpi_tb_verify_checksum(table_desc->pointer, + table_desc->length); + } - status = - acpi_tb_verify_checksum(table_desc->pointer, table_desc->length); return_ACPI_STATUS(status); } @@ -93,7 +97,7 @@ acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc) * * FUNCTION: acpi_tb_add_table * - * PARAMETERS: Table - Pointer to the table header + * PARAMETERS: table_desc - Table descriptor * table_index - Where the table index is returned * * RETURN: Status @@ -103,7 +107,7 @@ acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc) ******************************************************************************/ acpi_status -acpi_tb_add_table(struct acpi_table_header *table, +acpi_tb_add_table(struct acpi_table_desc *table_desc, acpi_native_uint * table_index) { acpi_native_uint i; @@ -112,6 +116,25 @@ acpi_tb_add_table(struct acpi_table_header *table, ACPI_FUNCTION_TRACE(tb_add_table); + if (!table_desc->pointer) { + status = acpi_tb_verify_table(table_desc); + if (ACPI_FAILURE(status) || !table_desc->pointer) { + return_ACPI_STATUS(status); + } + } + + /* The table must be either an SSDT or a PSDT */ + + if ((!ACPI_COMPARE_NAME(table_desc->pointer->signature, ACPI_SIG_PSDT)) + && + (!ACPI_COMPARE_NAME(table_desc->pointer->signature, ACPI_SIG_SSDT))) + { + ACPI_ERROR((AE_INFO, + "Table has invalid signature [%4.4s], must be SSDT or PSDT", + table_desc->pointer->signature)); + return_ACPI_STATUS(AE_BAD_SIGNATURE); + } + (void)acpi_ut_acquire_mutex(ACPI_MTX_TABLES); /* Check if table is already registered */ @@ -127,18 +150,17 @@ acpi_tb_add_table(struct acpi_table_header *table, } } - length = ACPI_MIN(table->length, - acpi_gbl_root_table_list.tables[i].pointer-> - length); - if (ACPI_MEMCMP - (table, acpi_gbl_root_table_list.tables[i].pointer, - length)) { + length = ACPI_MIN(table_desc->length, + acpi_gbl_root_table_list.tables[i].length); + if (ACPI_MEMCMP(table_desc->pointer, + acpi_gbl_root_table_list.tables[i].pointer, + length)) { continue; } /* Table is already registered */ - ACPI_FREE(table); + acpi_tb_delete_table(table_desc); *table_index = i; goto release; } @@ -146,14 +168,14 @@ acpi_tb_add_table(struct acpi_table_header *table, /* * Add the table to the global table list */ - status = acpi_tb_store_table(ACPI_TO_INTEGER(table), - table, table->length, - ACPI_TABLE_ORIGIN_ALLOCATED, table_index); + status = acpi_tb_store_table(table_desc->address, table_desc->pointer, + table_desc->length, table_desc->flags, + table_index); if (ACPI_FAILURE(status)) { goto release; } - acpi_tb_print_table_header(0, table); + acpi_tb_print_table_header(table_desc->address, table_desc->pointer); release: (void)acpi_ut_release_mutex(ACPI_MTX_TABLES); @@ -282,25 +304,20 @@ acpi_tb_store_table(acpi_physical_address address, * ******************************************************************************/ -void acpi_tb_delete_table(acpi_native_uint table_index) +void acpi_tb_delete_table(struct acpi_table_desc *table_desc) { - struct acpi_table_desc *table_desc; - - /* table_index assumed valid */ - - table_desc = &acpi_gbl_root_table_list.tables[table_index]; - /* Table must be mapped or allocated */ - if (!table_desc->pointer) { return; } - - if (table_desc->flags & ACPI_TABLE_ORIGIN_MAPPED) { - acpi_tb_unmap(table_desc->pointer, table_desc->length, - table_desc->flags & ACPI_TABLE_ORIGIN_MASK); - } else if (table_desc->flags & ACPI_TABLE_ORIGIN_ALLOCATED) { + switch (table_desc->flags & ACPI_TABLE_ORIGIN_MASK) { + case ACPI_TABLE_ORIGIN_MAPPED: + acpi_os_unmap_memory(table_desc->pointer, table_desc->length); + break; + case ACPI_TABLE_ORIGIN_ALLOCATED: ACPI_FREE(table_desc->pointer); + break; + default:; } table_desc->pointer = NULL; @@ -329,7 +346,7 @@ void acpi_tb_terminate(void) /* Delete the individual tables */ for (i = 0; i < acpi_gbl_root_table_list.count; ++i) { - acpi_tb_delete_table(i); + acpi_tb_delete_table(&acpi_gbl_root_table_list.tables[i]); } /* diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 1033748..0cb7439 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -462,49 +462,3 @@ acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags) return_ACPI_STATUS(AE_OK); } - -/****************************************************************************** - * - * FUNCTION: acpi_tb_map - * - * PARAMETERS: Address - Address to be mapped - * Length - Length to be mapped - * Flags - Logical or physical addressing mode - * - * RETURN: Pointer to mapped region - * - * DESCRIPTION: Maps memory according to flag - * - *****************************************************************************/ - -void *acpi_tb_map(acpi_physical_address address, u32 length, u32 flags) -{ - - if (flags == ACPI_TABLE_ORIGIN_MAPPED) { - return (acpi_os_map_memory(address, length)); - } else { - return (ACPI_CAST_PTR(void, address)); - } -} - -/****************************************************************************** - * - * FUNCTION: acpi_tb_unmap - * - * PARAMETERS: Pointer - To mapped region - * Length - Length to be unmapped - * Flags - Logical or physical addressing mode - * - * RETURN: None - * - * DESCRIPTION: Unmaps memory according to flag - * - *****************************************************************************/ - -void acpi_tb_unmap(void *pointer, u32 length, u32 flags) -{ - - if (flags == ACPI_TABLE_ORIGIN_MAPPED) { - acpi_os_unmap_memory(pointer, length); - } -} diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 9d451e8..77224bd 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -220,16 +220,25 @@ acpi_status acpi_load_table(struct acpi_table_header *table_ptr) { acpi_status status; acpi_native_uint table_index; + struct acpi_table_desc table_desc; + + if (!table_ptr) + return AE_BAD_PARAMETER; + + ACPI_MEMSET(&table_desc, 0, sizeof(struct acpi_table_desc)); + table_desc.pointer = table_ptr; + table_desc.length = table_ptr->length; + table_desc.flags = ACPI_TABLE_ORIGIN_UNKNOWN; /* * Install the new table into the local data structures */ - status = acpi_tb_add_table(table_ptr, &table_index); + status = acpi_tb_add_table(&table_desc, &table_index); if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); + return status; } status = acpi_ns_load_table(table_index, acpi_gbl_root_node); - return_ACPI_STATUS(status); + return status; } ACPI_EXPORT_SYMBOL(acpi_load_table) @@ -240,8 +249,7 @@ ACPI_EXPORT_SYMBOL(acpi_load_table) * * PARAMETERS: Signature - ACPI signature of needed table * Instance - Which instance (for SSDTs) - * out_table_header - Where the pointer to the table header - * is returned + * out_table_header - The pointer to the table header to fill * * RETURN: Status and pointer to mapped table header * @@ -254,10 +262,11 @@ ACPI_EXPORT_SYMBOL(acpi_load_table) acpi_status acpi_get_table_header(char *signature, acpi_native_uint instance, - struct acpi_table_header **out_table_header) + struct acpi_table_header *out_table_header) { acpi_native_uint i; acpi_native_uint j; + struct acpi_table_header *header; /* Parameter validation */ @@ -279,16 +288,31 @@ acpi_get_table_header(char *signature, continue; } - *out_table_header = - acpi_tb_map(acpi_gbl_root_table_list.tables[i].address, - (u32) sizeof(struct acpi_table_header), - acpi_gbl_root_table_list.tables[i]. - flags & ACPI_TABLE_ORIGIN_MASK); - - if (!(*out_table_header)) { - return (AE_NO_MEMORY); + if (!acpi_gbl_root_table_list.tables[i].pointer) { + if ((acpi_gbl_root_table_list.tables[i]. + flags & ACPI_TABLE_ORIGIN_MASK) == + ACPI_TABLE_ORIGIN_MAPPED) { + header = + acpi_os_map_memory(acpi_gbl_root_table_list. + tables[i].address, + sizeof(struct + acpi_table_header)); + if (!header) { + return AE_NO_MEMORY; + } + ACPI_MEMCPY(out_table_header, header, + sizeof(struct acpi_table_header)); + acpi_os_unmap_memory(header, + sizeof(struct + acpi_table_header)); + } else { + return AE_NOT_FOUND; + } + } else { + ACPI_MEMCPY(out_table_header, + acpi_gbl_root_table_list.tables[i].pointer, + sizeof(struct acpi_table_header)); } - return (AE_OK); } diff --git a/include/acpi/acpixf.h b/include/acpi/acpixf.h index 9c26400..918280e 100644 --- a/include/acpi/acpixf.h +++ b/include/acpi/acpixf.h @@ -109,7 +109,7 @@ acpi_status acpi_unload_table_id(acpi_owner_id id); acpi_status acpi_get_table_header(acpi_string signature, acpi_native_uint instance, - struct acpi_table_header **out_table_header); + struct acpi_table_header *out_table_header); acpi_status acpi_get_table(acpi_string signature, diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 4079f8a..5ef1b69 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -69,7 +69,7 @@ acpi_status acpi_tb_resize_root_table_list(void); acpi_status acpi_tb_verify_table(struct acpi_table_desc *table_desc); acpi_status -acpi_tb_add_table(struct acpi_table_header *table, +acpi_tb_add_table(struct acpi_table_desc *table_desc, acpi_native_uint * table_index); acpi_status @@ -77,7 +77,7 @@ acpi_tb_store_table(acpi_physical_address address, struct acpi_table_header *table, u32 length, u8 flags, acpi_native_uint * table_index); -void acpi_tb_delete_table(acpi_native_uint table_index); +void acpi_tb_delete_table(struct acpi_table_desc *table_desc); void acpi_tb_terminate(void); @@ -113,8 +113,4 @@ acpi_tb_install_table(acpi_physical_address address, acpi_status acpi_tb_parse_root_table(acpi_physical_address rsdp_address, u8 flags); -void *acpi_tb_map(acpi_physical_address address, u32 length, u32 flags); - -void acpi_tb_unmap(void *pointer, u32 length, u32 flags); - #endif /* __ACTABLES_H__ */ -- cgit v0.10.2 From a6823e12ca3f79a8c0f8b2d14976ab2152d117e5 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Fixes for load() operator. Optimized the Load operator in the case where the source operand is an operation region. Simply map the operation region memory, instead of performing a bytewise read. Signed-off-by: Bob Moore Signed-off-by: Len Brown diff --git a/drivers/acpi/executer/exconfig.c b/drivers/acpi/executer/exconfig.c index 7aa18f9..61ec855 100644 --- a/drivers/acpi/executer/exconfig.c +++ b/drivers/acpi/executer/exconfig.c @@ -119,7 +119,7 @@ acpi_ex_add_table(acpi_native_uint table_index, * * RETURN: Status * - * DESCRIPTION: Load an ACPI table + * DESCRIPTION: Load an ACPI table from the RSDT/XSDT * ******************************************************************************/ @@ -138,21 +138,7 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state, ACPI_FUNCTION_TRACE(ex_load_table_op); -#if 0 - /* - * Make sure that the signature does not match one of the tables that - * is already loaded. - */ - status = acpi_tb_match_signature(operand[0]->string.pointer, NULL); - if (status == AE_OK) { - - /* Signature matched -- don't allow override */ - - return_ACPI_STATUS(AE_ALREADY_EXISTS); - } -#endif - - /* Find the ACPI table */ + /* Find the ACPI table in the RSDT/XSDT */ status = acpi_tb_find_table(operand[0]->string.pointer, operand[1]->string.pointer, @@ -256,7 +242,7 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state, * * FUNCTION: acpi_ex_load_op * - * PARAMETERS: obj_desc - Region or Field where the table will be + * PARAMETERS: obj_desc - Region or Buffer/Field where the table will be * obtained * Target - Where a handle to the table will be stored * walk_state - Current state @@ -265,6 +251,12 @@ acpi_ex_load_table_op(struct acpi_walk_state *walk_state, * * DESCRIPTION: Load an ACPI table from a field or operation region * + * NOTE: Region Fields (Field, bank_field, index_fields) are resolved to buffer + * objects before this code is reached. + * + * If source is an operation region, it must refer to system_memory, as + * per the ACPI specification. + * ******************************************************************************/ acpi_status @@ -272,24 +264,26 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, union acpi_operand_object *target, struct acpi_walk_state *walk_state) { - acpi_status status; union acpi_operand_object *ddb_handle; - union acpi_operand_object *buffer_desc = NULL; - struct acpi_table_header *table_ptr = NULL; - acpi_native_uint table_index; - acpi_physical_address address; - struct acpi_table_header table_header; struct acpi_table_desc table_desc; - acpi_integer temp; - u32 i; + acpi_native_uint table_index; + acpi_status status; ACPI_FUNCTION_TRACE(ex_load_op); - /* Object can be either an op_region or a Field */ ACPI_MEMSET(&table_desc, 0, sizeof(struct acpi_table_desc)); + + /* Source Object can be either an op_region or a Buffer/Field */ + switch (ACPI_GET_OBJECT_TYPE(obj_desc)) { case ACPI_TYPE_REGION: + /* Region must be system_memory (from ACPI spec) */ + + if (obj_desc->region.space_id != ACPI_ADR_SPACE_SYSTEM_MEMORY) { + return_ACPI_STATUS(AE_AML_OPERAND_TYPE); + } + ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Load from Region %p %s\n", obj_desc, acpi_ut_get_object_type_name(obj_desc))); @@ -305,113 +299,31 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, } } - /* Get the base physical address of the region */ - - address = obj_desc->region.address; - - /* Get part of the table header to get the table length */ - - table_header.length = 0; - for (i = 0; i < 8; i++) { - status = - acpi_ev_address_space_dispatch(obj_desc, ACPI_READ, - (acpi_physical_address) - (i + address), 8, - &temp); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - /* Get the one valid byte of the returned 64-bit value */ - - ACPI_CAST_PTR(u8, &table_header)[i] = (u8) temp; - } - - /* Sanity check the table length */ - - if (table_header.length < sizeof(struct acpi_table_header)) { - return_ACPI_STATUS(AE_BAD_HEADER); - } - - /* Allocate a buffer for the entire table */ - - table_ptr = ACPI_ALLOCATE(table_header.length); - if (!table_ptr) { - return_ACPI_STATUS(AE_NO_MEMORY); - } - - /* Get the entire table from the op region */ - - for (i = 0; i < table_header.length; i++) { - status = - acpi_ev_address_space_dispatch(obj_desc, ACPI_READ, - (acpi_physical_address) - (i + address), 8, - &temp); - if (ACPI_FAILURE(status)) { - goto cleanup; - } - - /* Get the one valid byte of the returned 64-bit value */ - - ACPI_CAST_PTR(u8, table_ptr)[i] = (u8) temp; - } + table_desc.address = obj_desc->region.address; + table_desc.length = obj_desc->region.length; + table_desc.flags = ACPI_TABLE_ORIGIN_MAPPED; break; - case ACPI_TYPE_LOCAL_REGION_FIELD: - case ACPI_TYPE_LOCAL_BANK_FIELD: - case ACPI_TYPE_LOCAL_INDEX_FIELD: + case ACPI_TYPE_BUFFER: /* Buffer or resolved region_field */ - ACPI_DEBUG_PRINT((ACPI_DB_EXEC, "Load from Field %p %s\n", - obj_desc, - acpi_ut_get_object_type_name(obj_desc))); + /* Simply extract the buffer from the buffer object */ - /* - * The length of the field must be at least as large as the table. - * Read the entire field and thus the entire table. Buffer is - * allocated during the read. - */ - status = - acpi_ex_read_data_from_field(walk_state, obj_desc, - &buffer_desc); - if (ACPI_FAILURE(status)) { - return_ACPI_STATUS(status); - } - - table_ptr = ACPI_CAST_PTR(struct acpi_table_header, - buffer_desc->buffer.pointer); - - /* All done with the buffer_desc, delete it */ - - buffer_desc->buffer.pointer = NULL; - acpi_ut_remove_reference(buffer_desc); + ACPI_DEBUG_PRINT((ACPI_DB_EXEC, + "Load from Buffer or Field %p %s\n", obj_desc, + acpi_ut_get_object_type_name(obj_desc))); - /* Sanity check the table length */ + table_desc.pointer = ACPI_CAST_PTR(struct acpi_table_header, + obj_desc->buffer.pointer); + table_desc.length = table_desc.pointer->length; + table_desc.flags = ACPI_TABLE_ORIGIN_ALLOCATED; - if (table_ptr->length < sizeof(struct acpi_table_header)) { - status = AE_BAD_HEADER; - goto cleanup; - } + obj_desc->buffer.pointer = NULL; break; default: return_ACPI_STATUS(AE_AML_OPERAND_TYPE); } - /* The table must be either an SSDT or a PSDT */ - - if ((!ACPI_COMPARE_NAME(table_ptr->signature, ACPI_SIG_PSDT)) && - (!ACPI_COMPARE_NAME(table_ptr->signature, ACPI_SIG_SSDT))) { - ACPI_ERROR((AE_INFO, - "Table has invalid signature [%4.4s], must be SSDT or PSDT", - table_ptr->signature)); - status = AE_BAD_SIGNATURE; - goto cleanup; - } - - table_desc.pointer = table_ptr; - table_desc.length = table_ptr->length; - table_desc.flags = ACPI_TABLE_ORIGIN_ALLOCATED; /* * Install the new table into the local data structures */ @@ -440,13 +352,9 @@ acpi_ex_load_op(union acpi_operand_object *obj_desc, return_ACPI_STATUS(status); } - ACPI_INFO((AE_INFO, - "Dynamic SSDT Load - OemId [%6.6s] OemTableId [%8.8s]", - table_ptr->oem_id, table_ptr->oem_table_id)); - cleanup: if (ACPI_FAILURE(status)) { - ACPI_FREE(table_ptr); + acpi_tb_delete_table(&table_desc); } return_ACPI_STATUS(status); } diff --git a/drivers/acpi/executer/exresop.c b/drivers/acpi/executer/exresop.c index 4c93d09..411d120 100644 --- a/drivers/acpi/executer/exresop.c +++ b/drivers/acpi/executer/exresop.c @@ -611,22 +611,20 @@ acpi_ex_resolve_operands(u16 opcode, } goto next_operand; - case ARGI_REGION_OR_FIELD: + case ARGI_REGION_OR_BUFFER: /* Used by Load() only */ - /* Need an operand of type REGION or a FIELD in a region */ + /* Need an operand of type REGION or a BUFFER (which could be a resolved region field) */ switch (ACPI_GET_OBJECT_TYPE(obj_desc)) { + case ACPI_TYPE_BUFFER: case ACPI_TYPE_REGION: - case ACPI_TYPE_LOCAL_REGION_FIELD: - case ACPI_TYPE_LOCAL_BANK_FIELD: - case ACPI_TYPE_LOCAL_INDEX_FIELD: /* Valid operand */ break; default: ACPI_ERROR((AE_INFO, - "Needed [Region/RegionField], found [%s] %p", + "Needed [Region/Buffer], found [%s] %p", acpi_ut_get_object_type_name (obj_desc), obj_desc)); diff --git a/include/acpi/acopcode.h b/include/acpi/acopcode.h index 7659a46..d71f5d9 100644 --- a/include/acpi/acopcode.h +++ b/include/acpi/acopcode.h @@ -257,7 +257,7 @@ #define ARGI_LLESSEQUAL_OP ARGI_INVALID_OPCODE #define ARGI_LNOT_OP ARGI_LIST1 (ARGI_INTEGER) #define ARGI_LNOTEQUAL_OP ARGI_INVALID_OPCODE -#define ARGI_LOAD_OP ARGI_LIST2 (ARGI_REGION_OR_FIELD,ARGI_TARGETREF) +#define ARGI_LOAD_OP ARGI_LIST2 (ARGI_REGION_OR_BUFFER,ARGI_TARGETREF) #define ARGI_LOAD_TABLE_OP ARGI_LIST6 (ARGI_STRING, ARGI_STRING, ARGI_STRING, ARGI_STRING, ARGI_STRING, ARGI_ANYTYPE) #define ARGI_LOCAL0 ARG_NONE #define ARGI_LOCAL1 ARG_NONE diff --git a/include/acpi/amlcode.h b/include/acpi/amlcode.h index cf18426..fd0c722 100644 --- a/include/acpi/amlcode.h +++ b/include/acpi/amlcode.h @@ -273,7 +273,7 @@ #define ARGI_DATAOBJECT 0x12 /* Buffer, String, package or reference to a Node - Used only by size_of operator */ #define ARGI_COMPLEXOBJ 0x13 /* Buffer, String, or package (Used by INDEX op only) */ #define ARGI_REF_OR_STRING 0x14 /* Reference or String (Used by DEREFOF op only) */ -#define ARGI_REGION_OR_FIELD 0x15 /* Used by LOAD op only */ +#define ARGI_REGION_OR_BUFFER 0x15 /* Used by LOAD op only */ #define ARGI_DATAREFOBJ 0x16 /* Note: types above can expand to 0x1F maximum */ -- cgit v0.10.2 From 8876016bb384044a59c1e2ddcad4cf41b06344b9 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:22 +0300 Subject: ACPICA: Remove global lock handler on AcpiTerminate. Added AcpiEvRemoveGlobalLockHandler Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index 545f934..db16300 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c @@ -73,6 +73,8 @@ static void ACPI_SYSTEM_XFACE acpi_ev_notify_dispatch(void *context); static u32 acpi_ev_global_lock_handler(void *context); +static acpi_status acpi_ev_remove_global_lock_handler(void); + /******************************************************************************* * * FUNCTION: acpi_ev_is_notify_object @@ -376,6 +378,31 @@ acpi_status acpi_ev_init_global_lock_handler(void) return_ACPI_STATUS(status); } +/******************************************************************************* + * + * FUNCTION: acpi_ev_remove_global_lock_handler + * + * PARAMETERS: None + * + * RETURN: Status + * + * DESCRIPTION: Remove the handler for the Global Lock + * + ******************************************************************************/ + +static acpi_status acpi_ev_remove_global_lock_handler(void) +{ + acpi_status status; + + ACPI_FUNCTION_TRACE(ev_remove_global_lock_handler); + + acpi_gbl_global_lock_present = FALSE; + status = acpi_remove_fixed_event_handler(ACPI_EVENT_GLOBAL, + acpi_ev_global_lock_handler); + + return_ACPI_STATUS(status); +} + /****************************************************************************** * * FUNCTION: acpi_ev_acquire_global_lock @@ -554,6 +581,12 @@ void acpi_ev_terminate(void) if (ACPI_FAILURE(status)) { ACPI_ERROR((AE_INFO, "Could not remove SCI handler")); } + + status = acpi_ev_remove_global_lock_handler(); + if (ACPI_FAILURE(status)) { + ACPI_ERROR((AE_INFO, + "Could not remove Global Lock handler")); + } } /* Deallocate all handler objects installed within GPE info structs */ -- cgit v0.10.2 From 7c9626bade13de3f160f0926455328650045d6cd Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Ensure that all structures in acobject.h are aligned, via #pragma. Thus, even if the default compiler setting is non-aligned, the header is compiled correctly. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acobject.h b/include/acpi/acobject.h index 8fdee31..b81e923 100644 --- a/include/acpi/acobject.h +++ b/include/acpi/acobject.h @@ -52,7 +52,15 @@ * to the interpreter, and to keep track of the various handlers such as * address space handlers and notify handlers. The object is a constant * size in order to allow it to be cached and reused. + * + * Note: The object is optimized to be aligned and will not work if it is + * byte-packed. */ +#if ACPI_MACHINE_WIDTH == 64 +#pragma pack(8) +#else +#pragma pack(4) +#endif /******************************************************************************* * @@ -101,7 +109,8 @@ struct acpi_object_common { ACPI_OBJECT_COMMON_HEADER}; struct acpi_object_integer { - ACPI_OBJECT_COMMON_HEADER acpi_integer value; + ACPI_OBJECT_COMMON_HEADER u8 fill[3]; /* Prevent warning on some compilers */ + acpi_integer value; }; /* @@ -203,7 +212,9 @@ struct acpi_object_power_resource { }; struct acpi_object_processor { - ACPI_OBJECT_COMMON_HEADER u8 proc_id; + ACPI_OBJECT_COMMON_HEADER + /* The next two fields take advantage of the 3-byte space before NOTIFY_INFO */ + u8 proc_id; u8 length; ACPI_COMMON_NOTIFY_INFO acpi_io_address address; }; @@ -406,4 +417,6 @@ union acpi_descriptor { union acpi_parse_object op; }; +#pragma pack() + #endif /* _ACOBJECT_H */ diff --git a/include/acpi/actypes.h b/include/acpi/actypes.h index 6fa3f2a..d213f97 100644 --- a/include/acpi/actypes.h +++ b/include/acpi/actypes.h @@ -156,6 +156,7 @@ typedef u64 acpi_physical_address; #define ACPI_MAX_PTR ACPI_UINT64_MAX #define ACPI_SIZE_MAX ACPI_UINT64_MAX +#define ACPI_NATIVE_BOUNDARY 8 #define ACPI_USE_NATIVE_DIVIDE /* Has native 64-bit integer support */ /* @@ -196,6 +197,8 @@ typedef u32 acpi_physical_address; #define ACPI_MAX_PTR ACPI_UINT32_MAX #define ACPI_SIZE_MAX ACPI_UINT32_MAX +#define ACPI_NATIVE_BOUNDARY 4 + /******************************************************************************* * * Types specific to 16-bit targets @@ -222,6 +225,7 @@ typedef char *acpi_physical_address; #define ACPI_MAX_PTR ACPI_UINT16_MAX #define ACPI_SIZE_MAX ACPI_UINT16_MAX +#define ACPI_NATIVE_BOUNDARY 2 #define ACPI_USE_NATIVE_DIVIDE /* No 64-bit integers, ok to use native divide */ /* 64-bit integers cannot be supported */ -- cgit v0.10.2 From 987c21a0b0081d480ec3cd04875509cdc10e15e7 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Add ACPI_MAX macro Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acmacros.h b/include/acpi/acmacros.h index 192fa09..9b2e4d7 100644 --- a/include/acpi/acmacros.h +++ b/include/acpi/acmacros.h @@ -55,6 +55,7 @@ #define ACPI_SET_BIT(target,bit) ((target) |= (bit)) #define ACPI_CLEAR_BIT(target,bit) ((target) &= ~(bit)) #define ACPI_MIN(a,b) (((a)<(b))?(a):(b)) +#define ACPI_MAX(a,b) (((a)>(b))?(a):(b)) /* Size calculation */ -- cgit v0.10.2 From c857303ad496e1f52955e95994a67869882e89f9 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Fail AcpiEnable if ACPI tables not loaded. AcpiEnable will now fail if all of the required ACPI tables are not loaded (FADT, FACS, DSDT). BZ 477 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evxfevnt.c b/drivers/acpi/events/evxfevnt.c index a3d148e..4eab4f5 100644 --- a/drivers/acpi/events/evxfevnt.c +++ b/drivers/acpi/events/evxfevnt.c @@ -65,6 +65,14 @@ acpi_status acpi_enable(void) ACPI_FUNCTION_TRACE(acpi_enable); + /* ACPI tables must be present */ + + if (!acpi_tb_tables_loaded()) { + return_ACPI_STATUS(AE_NO_ACPI_TABLES); + } + + /* Check current mode */ + if (acpi_hw_get_mode() == ACPI_SYS_MODE_ACPI) { ACPI_DEBUG_PRINT((ACPI_DB_INIT, "System is already in ACPI mode\n")); diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 0cb7439..0874ab2 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -54,6 +54,29 @@ acpi_tb_get_root_table_entry(u8 * table_entry, /******************************************************************************* * + * FUNCTION: acpi_tb_tables_loaded + * + * PARAMETERS: None + * + * RETURN: TRUE if required ACPI tables are loaded + * + * DESCRIPTION: Determine if the minimum required ACPI tables are present + * (FADT, FACS, DSDT) + * + ******************************************************************************/ + +u8 acpi_tb_tables_loaded(void) +{ + + if (acpi_gbl_root_table_list.count >= 3) { + return (TRUE); + } + + return (FALSE); +} + +/******************************************************************************* + * * FUNCTION: acpi_tb_print_table_header * * PARAMETERS: Address - Table physical address diff --git a/include/acpi/actables.h b/include/acpi/actables.h index 5ef1b69..e7efb8a 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -97,6 +97,8 @@ void acpi_tb_set_table_loaded_flag(acpi_native_uint table_index, u8 is_loaded); /* * tbutils - table manager utilities */ +u8 acpi_tb_tables_loaded(void); + void acpi_tb_print_table_header(acpi_physical_address address, struct acpi_table_header *header); -- cgit v0.10.2 From 1a666f8be16a0e1580e0f37e1322d06affb84e1b Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Add include of actables.h Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evxfevnt.c b/drivers/acpi/events/evxfevnt.c index 4eab4f5..bbd631d 100644 --- a/drivers/acpi/events/evxfevnt.c +++ b/drivers/acpi/events/evxfevnt.c @@ -44,6 +44,7 @@ #include #include #include +#include #define _COMPONENT ACPI_EVENTS ACPI_MODULE_NAME("evxfevnt") -- cgit v0.10.2 From ff40c8a3f258e9a54b0b94b92d5e2d9d88a39954 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Update version to 20061109 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index 9aa3b19..755340b 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20061011 +#define ACPI_CA_VERSION 0x20061109 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, -- cgit v0.10.2 From 59fa85057e12ff135df54266722b2064c418fc05 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Removed all 16-bit support. Support for 16-bit ACPICA has been completely removed since it is no longer necessary and it clutters the code. All 16-bit macros, types, and conditional compiles have been removed, cleaning up and simplifying the code across the entire subsystem. DOS support is no longer needed since the Linux firmware kit is now available. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/events/evgpeblk.c b/drivers/acpi/events/evgpeblk.c index 8a6f01a..a23634c 100644 --- a/drivers/acpi/events/evgpeblk.c +++ b/drivers/acpi/events/evgpeblk.c @@ -796,12 +796,12 @@ acpi_ev_create_gpe_info_blocks(struct acpi_gpe_block_info *gpe_block) (u8) (gpe_block->block_base_number + (i * ACPI_GPE_REGISTER_WIDTH)); - ACPI_STORE_ADDRESS(this_register->status_address.address, - (gpe_block->block_address.address + i)); + this_register->status_address.address = + gpe_block->block_address.address + i; - ACPI_STORE_ADDRESS(this_register->enable_address.address, - (gpe_block->block_address.address - + i + gpe_block->register_count)); + this_register->enable_address.address = + gpe_block->block_address.address + i + + gpe_block->register_count; this_register->status_address.space_id = gpe_block->block_address.space_id; diff --git a/drivers/acpi/executer/exoparg1.c b/drivers/acpi/executer/exoparg1.c index 6374d8b..6f2e69c 100644 --- a/drivers/acpi/executer/exoparg1.c +++ b/drivers/acpi/executer/exoparg1.c @@ -104,9 +104,7 @@ acpi_status acpi_ex_opcode_0A_0T_1R(struct acpi_walk_state *walk_state) status = AE_NO_MEMORY; goto cleanup; } -#if ACPI_MACHINE_WIDTH != 16 return_desc->integer.value = acpi_os_get_timer(); -#endif break; default: /* Unknown opcode */ diff --git a/drivers/acpi/executer/exregion.c b/drivers/acpi/executer/exregion.c index 4967447..c6819e0 100644 --- a/drivers/acpi/executer/exregion.c +++ b/drivers/acpi/executer/exregion.c @@ -209,11 +209,10 @@ acpi_ex_system_memory_space_handler(u32 function, *value = (acpi_integer) ACPI_GET32(logical_addr_ptr); break; -#if ACPI_MACHINE_WIDTH != 16 case 64: *value = (acpi_integer) ACPI_GET64(logical_addr_ptr); break; -#endif + default: /* bit_width was already validated */ break; @@ -235,11 +234,9 @@ acpi_ex_system_memory_space_handler(u32 function, ACPI_SET32(logical_addr_ptr) = (u32) * value; break; -#if ACPI_MACHINE_WIDTH != 16 case 64: ACPI_SET64(logical_addr_ptr) = (u64) * value; break; -#endif default: /* bit_width was already validated */ diff --git a/drivers/acpi/hardware/hwregs.c b/drivers/acpi/hardware/hwregs.c index 716e4ae..5b19fc7 100644 --- a/drivers/acpi/hardware/hwregs.c +++ b/drivers/acpi/hardware/hwregs.c @@ -788,8 +788,8 @@ acpi_hw_low_level_read(u32 width, u32 * value, struct acpi_generic_address *reg) case ACPI_ADR_SPACE_SYSTEM_IO: - status = acpi_os_read_port((acpi_io_address) address, - value, width); + status = + acpi_os_read_port((acpi_io_address) address, value, width); break; default: @@ -800,8 +800,7 @@ acpi_hw_low_level_read(u32 width, u32 * value, struct acpi_generic_address *reg) ACPI_DEBUG_PRINT((ACPI_DB_IO, "Read: %8.8X width %2d from %8.8X%8.8X (%s)\n", - *value, width, - ACPI_FORMAT_UINT64(address), + *value, width, ACPI_FORMAT_UINT64(address), acpi_ut_get_region_name(reg->space_id))); return (status); @@ -858,8 +857,8 @@ acpi_hw_low_level_write(u32 width, u32 value, struct acpi_generic_address * reg) case ACPI_ADR_SPACE_SYSTEM_IO: - status = acpi_os_write_port((acpi_io_address) address, - value, width); + status = acpi_os_write_port((acpi_io_address) address, value, + width); break; default: @@ -870,8 +869,7 @@ acpi_hw_low_level_write(u32 width, u32 value, struct acpi_generic_address * reg) ACPI_DEBUG_PRINT((ACPI_DB_IO, "Wrote: %8.8X width %2d to %8.8X%8.8X (%s)\n", - value, width, - ACPI_FORMAT_UINT64(address), + value, width, ACPI_FORMAT_UINT64(address), acpi_ut_get_region_name(reg->space_id))); return (status); diff --git a/drivers/acpi/tables/tbxfroot.c b/drivers/acpi/tables/tbxfroot.c index 5c6e882..82c0b66 100644 --- a/drivers/acpi/tables/tbxfroot.c +++ b/drivers/acpi/tables/tbxfroot.c @@ -98,8 +98,6 @@ static acpi_status acpi_tb_validate_rsdp(struct acpi_table_rsdp *rsdp) return (AE_OK); } -#if ACPI_MACHINE_WIDTH != 16 - /******************************************************************************* * * FUNCTION: acpi_tb_find_rsdp @@ -275,5 +273,3 @@ static u8 *acpi_tb_scan_memory_for_rsdp(u8 * start_address, u32 length) start_address)); return_PTR(NULL); } - -#endif diff --git a/include/acpi/acmacros.h b/include/acpi/acmacros.h index 9b2e4d7..549e533 100644 --- a/include/acpi/acmacros.h +++ b/include/acpi/acmacros.h @@ -61,20 +61,6 @@ #define ACPI_ARRAY_LENGTH(x) (sizeof(x) / sizeof((x)[0])) -#if ACPI_MACHINE_WIDTH == 16 - -/* - * For 16-bit addresses, we have to assume that the upper 32 bits - * (out of 64) are zero. - */ -#define ACPI_LODWORD(l) ((u32)(l)) -#define ACPI_HIDWORD(l) ((u32)(0)) - -#define ACPI_GET_ADDRESS(a) ((a).lo) -#define ACPI_STORE_ADDRESS(a,b) {(a).hi=0;(a).lo=(u32)(b);} -#define ACPI_VALID_ADDRESS(a) ((a).hi | (a).lo) - -#else #ifdef ACPI_NO_INTEGER64_SUPPORT /* * acpi_integer is 32-bits, no 64-bit support on this platform @@ -82,10 +68,6 @@ #define ACPI_LODWORD(l) ((u32)(l)) #define ACPI_HIDWORD(l) ((u32)(0)) -#define ACPI_GET_ADDRESS(a) (a) -#define ACPI_STORE_ADDRESS(a,b) ((a)=(b)) -#define ACPI_VALID_ADDRESS(a) (a) - #else /* @@ -93,11 +75,6 @@ */ #define ACPI_LODWORD(l) ((u32)(u64)(l)) #define ACPI_HIDWORD(l) ((u32)(((*(struct uint64_struct *)(void *)(&l))).hi)) - -#define ACPI_GET_ADDRESS(a) (a) -#define ACPI_STORE_ADDRESS(a,b) ((a)=(acpi_physical_address)(b)) -#define ACPI_VALID_ADDRESS(a) (a) -#endif #endif /* @@ -135,15 +112,8 @@ #define ACPI_TO_POINTER(i) ACPI_ADD_PTR (void,(void *) NULL,(acpi_native_uint) i) #define ACPI_TO_INTEGER(p) ACPI_PTR_DIFF (p,(void *) NULL) #define ACPI_OFFSET(d,f) (acpi_size) ACPI_PTR_DIFF (&(((d *)0)->f),(void *) NULL) - -#if ACPI_MACHINE_WIDTH == 16 -#define ACPI_STORE_POINTER(d,s) ACPI_MOVE_32_TO_32(d,s) -#define ACPI_PHYSADDR_TO_PTR(i) (void *)(i) -#define ACPI_PTR_TO_PHYSADDR(i) (u32) ACPI_CAST_PTR (u8,(i)) -#else #define ACPI_PHYSADDR_TO_PTR(i) ACPI_TO_POINTER(i) #define ACPI_PTR_TO_PHYSADDR(i) ACPI_TO_INTEGER(i) -#endif #ifndef ACPI_MISALIGNMENT_NOT_SUPPORTED #define ACPI_COMPARE_NAME(a,b) (*ACPI_CAST_PTR (u32,(a)) == *ACPI_CAST_PTR (u32,(b))) @@ -224,28 +194,6 @@ /* The hardware supports unaligned transfers, just do the little-endian move */ -#if ACPI_MACHINE_WIDTH == 16 - -/* No 64-bit integers */ -/* 16-bit source, 16/32/64 destination */ - -#define ACPI_MOVE_16_TO_16(d,s) *(u16 *)(void *)(d) = *(u16 *)(void *)(s) -#define ACPI_MOVE_16_TO_32(d,s) *(u32 *)(void *)(d) = *(u16 *)(void *)(s) -#define ACPI_MOVE_16_TO_64(d,s) ACPI_MOVE_16_TO_32(d,s) - -/* 32-bit source, 16/32/64 destination */ - -#define ACPI_MOVE_32_TO_16(d,s) ACPI_MOVE_16_TO_16(d,s) /* Truncate to 16 */ -#define ACPI_MOVE_32_TO_32(d,s) *(u32 *)(void *)(d) = *(u32 *)(void *)(s) -#define ACPI_MOVE_32_TO_64(d,s) ACPI_MOVE_32_TO_32(d,s) - -/* 64-bit source, 16/32/64 destination */ - -#define ACPI_MOVE_64_TO_16(d,s) ACPI_MOVE_16_TO_16(d,s) /* Truncate to 16 */ -#define ACPI_MOVE_64_TO_32(d,s) ACPI_MOVE_32_TO_32(d,s) /* Truncate to 32 */ -#define ACPI_MOVE_64_TO_64(d,s) ACPI_MOVE_32_TO_32(d,s) - -#else /* 16-bit source, 16/32/64 destination */ #define ACPI_MOVE_16_TO_16(d,s) *(u16 *)(void *)(d) = *(u16 *)(void *)(s) @@ -263,7 +211,6 @@ #define ACPI_MOVE_64_TO_16(d,s) ACPI_MOVE_16_TO_16(d,s) /* Truncate to 16 */ #define ACPI_MOVE_64_TO_32(d,s) ACPI_MOVE_32_TO_32(d,s) /* Truncate to 32 */ #define ACPI_MOVE_64_TO_64(d,s) *(u64 *)(void *)(d) = *(u64 *)(void *)(s) -#endif #else /* @@ -308,10 +255,7 @@ /* Macros based on machine integer width */ -#if ACPI_MACHINE_WIDTH == 16 -#define ACPI_MOVE_SIZE_TO_16(d,s) ACPI_MOVE_16_TO_16(d,s) - -#elif ACPI_MACHINE_WIDTH == 32 +#if ACPI_MACHINE_WIDTH == 32 #define ACPI_MOVE_SIZE_TO_16(d,s) ACPI_MOVE_32_TO_16(d,s) #elif ACPI_MACHINE_WIDTH == 64 @@ -696,16 +640,6 @@ #define ACPI_DEBUGGER_EXEC(a) #endif -/* - * For 16-bit code, we want to shrink some things even though - * we are using ACPI_DEBUG_OUTPUT to get the debug output - */ -#if ACPI_MACHINE_WIDTH == 16 -#undef ACPI_DEBUG_ONLY_MEMBERS -#undef _VERBOSE_STRUCTURES -#define ACPI_DEBUG_ONLY_MEMBERS(a) -#endif - #ifdef ACPI_DEBUG_OUTPUT /* * 1) Set name to blanks diff --git a/include/acpi/actypes.h b/include/acpi/actypes.h index d213f97..fff2d24 100644 --- a/include/acpi/actypes.h +++ b/include/acpi/actypes.h @@ -149,14 +149,12 @@ typedef int INT32; typedef u64 acpi_native_uint; typedef s64 acpi_native_int; -typedef u64 acpi_table_ptr; typedef u64 acpi_io_address; typedef u64 acpi_physical_address; #define ACPI_MAX_PTR ACPI_UINT64_MAX #define ACPI_SIZE_MAX ACPI_UINT64_MAX -#define ACPI_NATIVE_BOUNDARY 8 #define ACPI_USE_NATIVE_DIVIDE /* Has native 64-bit integer support */ /* @@ -190,51 +188,15 @@ typedef int INT32; typedef u32 acpi_native_uint; typedef s32 acpi_native_int; -typedef u64 acpi_table_ptr; typedef u32 acpi_io_address; typedef u32 acpi_physical_address; #define ACPI_MAX_PTR ACPI_UINT32_MAX #define ACPI_SIZE_MAX ACPI_UINT32_MAX -#define ACPI_NATIVE_BOUNDARY 4 - -/******************************************************************************* - * - * Types specific to 16-bit targets - * - ******************************************************************************/ - -#elif ACPI_MACHINE_WIDTH == 16 - -/*! [Begin] no source code translation (keep the typedefs as-is) */ - -typedef unsigned long UINT32; -typedef short INT16; -typedef long INT32; - -/*! [End] no source code translation !*/ - -typedef u16 acpi_native_uint; -typedef s16 acpi_native_int; - -typedef u32 acpi_table_ptr; -typedef u32 acpi_io_address; -typedef char *acpi_physical_address; - -#define ACPI_MAX_PTR ACPI_UINT16_MAX -#define ACPI_SIZE_MAX ACPI_UINT16_MAX - -#define ACPI_NATIVE_BOUNDARY 2 -#define ACPI_USE_NATIVE_DIVIDE /* No 64-bit integers, ok to use native divide */ - -/* 64-bit integers cannot be supported */ - -#define ACPI_NO_INTEGER64_SUPPORT - #else -/* ACPI_MACHINE_WIDTH must be either 64, 32, or 16 */ +/* ACPI_MACHINE_WIDTH must be either 64 or 32 */ #error unknown ACPI_MACHINE_WIDTH #endif -- cgit v0.10.2 From 2e23f8513e9d0cc6d07d36e4555badc2518df433 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Debugger multithreading enhancements. Implemented enhancements to the multithreading support within the debugger to enable better multithreading evaluation of the subsystem. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acdebug.h b/include/acpi/acdebug.h index d816709..47296ff 100644 --- a/include/acpi/acdebug.h +++ b/include/acpi/acdebug.h @@ -214,4 +214,6 @@ void acpi_db_prep_namestring(char *name); struct acpi_namespace_node *acpi_db_local_ns_lookup(char *name); +void acpi_db_uint32_to_hex_string(u32 value, char *buffer); + #endif /* __ACDEBUG_H__ */ diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index 7b28d93..9b7e05c 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -872,12 +872,30 @@ struct acpi_bit_register_info { ****************************************************************************/ struct acpi_db_method_info { - acpi_handle thread_gate; + acpi_handle main_thread_gate; + acpi_handle thread_complete_gate; + u32 *threads; + u32 num_threads; + u32 num_created; + u32 num_completed; + char *name; - char **args; u32 flags; u32 num_loops; char pathname[128]; + char **args; + + /* + * Arguments to be passed to method for the command + * Threads - + * the Number of threads, ID of current thread and + * Index of current thread inside all them created. + */ + char init_args; + char *arguments[4]; + char num_threads_str[11]; + char id_of_thread_str[11]; + char index_of_thread_str[11]; }; struct acpi_integrity_info { -- cgit v0.10.2 From ea5415785146afe37dd2d1179a6c3a34fd26b52f Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Update a comment. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/actypes.h b/include/acpi/actypes.h index fff2d24..ee1a118 100644 --- a/include/acpi/actypes.h +++ b/include/acpi/actypes.h @@ -48,7 +48,8 @@ /* * ACPI_MACHINE_WIDTH must be specified in an OS- or compiler-dependent header - * and must be either 16, 32, or 64 + * and must be either 32 or 64. 16-bit ACPICA is no longer supported, as of + * 12/2006. */ #ifndef ACPI_MACHINE_WIDTH #error ACPI_MACHINE_WIDTH not defined -- cgit v0.10.2 From afbb9e659d584bd5bf0604848c91afd5761ed7a1 Mon Sep 17 00:00:00 2001 From: "Valery A. Podrezov" Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Enhance debugger statistics/memory command. Debugger: Enhanced the Statistics/Memory command to emit the total (maximum) memory used during execution, as well as the maximum memory consumed by each of the various object types. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/namespace/nsalloc.c b/drivers/acpi/namespace/nsalloc.c index 55b407a..1e6a1b0 100644 --- a/drivers/acpi/namespace/nsalloc.c +++ b/drivers/acpi/namespace/nsalloc.c @@ -61,6 +61,9 @@ ACPI_MODULE_NAME("nsalloc") struct acpi_namespace_node *acpi_ns_create_node(u32 name) { struct acpi_namespace_node *node; +#ifdef ACPI_DBG_TRACK_ALLOCATIONS + u32 temp; +#endif ACPI_FUNCTION_TRACE(ns_create_node); @@ -71,6 +74,15 @@ struct acpi_namespace_node *acpi_ns_create_node(u32 name) ACPI_MEM_TRACKING(acpi_gbl_ns_node_list->total_allocated++); +#ifdef ACPI_DBG_TRACK_ALLOCATIONS + temp = + acpi_gbl_ns_node_list->total_allocated - + acpi_gbl_ns_node_list->total_freed; + if (temp > acpi_gbl_ns_node_list->max_occupied) { + acpi_gbl_ns_node_list->max_occupied = temp; + } +#endif + node->name.integer = name; ACPI_SET_DESCRIPTOR_TYPE(node, ACPI_DESC_TYPE_NAMED); return_PTR(node); diff --git a/drivers/acpi/utilities/utcache.c b/drivers/acpi/utilities/utcache.c index 1a1f810..d796fca 100644 --- a/drivers/acpi/utilities/utcache.c +++ b/drivers/acpi/utilities/utcache.c @@ -289,6 +289,14 @@ void *acpi_os_acquire_object(struct acpi_memory_list *cache) ACPI_MEM_TRACKING(cache->total_allocated++); +#ifdef ACPI_DBG_TRACK_ALLOCATIONS + if ((cache->total_allocated - cache->total_freed) > + cache->max_occupied) { + cache->max_occupied = + cache->total_allocated - cache->total_freed; + } +#endif + /* Avoid deadlock with ACPI_ALLOCATE_ZEROED */ status = acpi_ut_release_mutex(ACPI_MTX_CACHES); diff --git a/include/acpi/acdebug.h b/include/acpi/acdebug.h index 47296ff..c46a33a 100644 --- a/include/acpi/acdebug.h +++ b/include/acpi/acdebug.h @@ -159,6 +159,10 @@ void acpi_db_create_execution_threads(char *num_threads_arg, char *num_loops_arg, char *method_name_arg); +#ifdef ACPI_DBG_TRACK_ALLOCATIONS +u32 acpi_db_get_cache_info(struct acpi_memory_list *cache); +#endif + /* * dbfileio - Debugger file I/O commands */ diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index 9b7e05c..e135dab 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -954,6 +954,8 @@ struct acpi_memory_list { u32 total_allocated; u32 total_freed; + u32 max_occupied; + u32 total_size; u32 current_total_size; u32 requests; u32 hits; -- cgit v0.10.2 From d41eb99bac4063aa3fac2dbb8ca01bedd9f0b3bf Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Added option to display memory statistics upon termination. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/utilities/utalloc.c b/drivers/acpi/utilities/utalloc.c index f6cbc0b..b716797 100644 --- a/drivers/acpi/utilities/utalloc.c +++ b/drivers/acpi/utilities/utalloc.c @@ -42,6 +42,7 @@ */ #include +#include #define _COMPONENT ACPI_UTILITIES ACPI_MODULE_NAME("utalloc") @@ -142,6 +143,14 @@ acpi_status acpi_ut_create_caches(void) acpi_status acpi_ut_delete_caches(void) { +#ifdef ACPI_DBG_TRACK_ALLOCATIONS + char buffer[7]; + + if (acpi_gbl_display_final_mem_stats) { + ACPI_STRCPY(buffer, "MEMORY"); + acpi_db_display_statistics(buffer); + } +#endif (void)acpi_os_delete_cache(acpi_gbl_namespace_cache); acpi_gbl_namespace_cache = NULL; diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 509a85d..62929f4 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -727,6 +727,10 @@ void acpi_ut_init_globals(void) acpi_gbl_lowest_stack_pointer = ACPI_SIZE_MAX; #endif +#ifdef ACPI_DBG_TRACK_ALLOCATIONS + acpi_gbl_display_final_mem_stats = FALSE; +#endif + return_VOID; } diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index d1a5363..5b5d437 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -200,6 +200,7 @@ ACPI_EXTERN spinlock_t _acpi_gbl_hardware_lock; /* For ACPI H/W except GPE regis ACPI_EXTERN struct acpi_memory_list *acpi_gbl_global_list; ACPI_EXTERN struct acpi_memory_list *acpi_gbl_ns_node_list; +ACPI_EXTERN u8 acpi_gbl_display_final_mem_stats; #endif /* Object caches */ -- cgit v0.10.2 From 5008740e27540e4069a2f8235f8308aba46036a2 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Update version to 20061215 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index 755340b..aaa2813 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20061109 +#define ACPI_CA_VERSION 0x20061215 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, -- cgit v0.10.2 From f18c5a08bf035b51939281f5b49aa3ae45cea6ce Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Allow ACPI id to be u32 instead of u8. Allow ACPI id to be u32 instead of u8. Requires drop of conversion tables with the acpiid as index. Signed-off-by: Len Brown diff --git a/arch/i386/kernel/acpi/boot.c b/arch/i386/kernel/acpi/boot.c index 2147511..e94aff6 100644 --- a/arch/i386/kernel/acpi/boot.c +++ b/arch/i386/kernel/acpi/boot.c @@ -92,11 +92,6 @@ static u64 acpi_lapic_addr __initdata = APIC_DEFAULT_PHYS_BASE; #warning ACPI uses CMPXCHG, i486 and later hardware #endif -#define MAX_MADT_ENTRIES 256 -u8 x86_acpiid_to_apicid[MAX_MADT_ENTRIES] = - {[0 ... MAX_MADT_ENTRIES - 1] = 0xff }; -EXPORT_SYMBOL(x86_acpiid_to_apicid); - /* -------------------------------------------------------------------------- Boot-time Configuration -------------------------------------------------------------------------- */ @@ -253,10 +248,6 @@ acpi_parse_lapic(struct acpi_subtable_header * header, const unsigned long end) acpi_table_print_madt_entry(header); - /* Record local apic id only when enabled */ - if (processor->lapic_flags & ACPI_MADT_ENABLED) - x86_acpiid_to_apicid[processor->processor_id] = processor->id; - /* * We need to register disabled CPU as well to permit * counting disabled CPUs. This allows us to size @@ -563,14 +554,6 @@ EXPORT_SYMBOL(acpi_map_lsapic); int acpi_unmap_lsapic(int cpu) { - int i; - - for_each_possible_cpu(i) { - if (x86_acpiid_to_apicid[i] == x86_cpu_to_apicid[cpu]) { - x86_acpiid_to_apicid[i] = -1; - break; - } - } x86_cpu_to_apicid[cpu] = -1; cpu_clear(cpu, cpu_present_map); num_processors--; diff --git a/arch/ia64/kernel/acpi.c b/arch/ia64/kernel/acpi.c index 4719e48..989ffc3 100644 --- a/arch/ia64/kernel/acpi.c +++ b/arch/ia64/kernel/acpi.c @@ -67,11 +67,6 @@ EXPORT_SYMBOL(pm_power_off); unsigned int acpi_cpei_override; unsigned int acpi_cpei_phys_cpuid; -#define MAX_SAPICS 256 -u16 ia64_acpiid_to_sapicid[MAX_SAPICS] = {[0 ... MAX_SAPICS - 1] = -1 }; - -EXPORT_SYMBOL(ia64_acpiid_to_sapicid); - const char *acpi_get_sysname(void) { #ifdef CONFIG_IA64_GENERIC @@ -200,8 +195,6 @@ acpi_parse_lsapic(struct acpi_subtable_header * header, const unsigned long end) smp_boot_data.cpu_phys_id[available_cpus] = (lsapic->id << 8) | lsapic->eid; #endif - ia64_acpiid_to_sapicid[lsapic->processor_id] = - (lsapic->id << 8) | lsapic->eid; ++available_cpus; } @@ -880,7 +873,6 @@ int acpi_map_lsapic(acpi_handle handle, int *pcpu) cpu_set(cpu, cpu_present_map); ia64_cpu_to_sapicid[cpu] = physid; - ia64_acpiid_to_sapicid[lsapic->processor_id] = ia64_cpu_to_sapicid[cpu]; *pcpu = cpu; return (0); @@ -890,14 +882,6 @@ EXPORT_SYMBOL(acpi_map_lsapic); int acpi_unmap_lsapic(int cpu) { - int i; - - for (i = 0; i < MAX_SAPICS; i++) { - if (ia64_acpiid_to_sapicid[i] == ia64_cpu_to_sapicid[cpu]) { - ia64_acpiid_to_sapicid[i] = -1; - break; - } - } ia64_cpu_to_sapicid[cpu] = -1; cpu_clear(cpu, cpu_present_map); diff --git a/drivers/acpi/processor_core.c b/drivers/acpi/processor_core.c index 1b6bc66..6893c0b 100644 --- a/drivers/acpi/processor_core.c +++ b/drivers/acpi/processor_core.c @@ -375,30 +375,126 @@ static int acpi_processor_remove_fs(struct acpi_device *device) } /* Use the acpiid in MADT to map cpus in case of SMP */ + #ifndef CONFIG_SMP #define convert_acpiid_to_cpu(acpi_id) (-1) #else +static struct acpi_table_madt *madt; + +static int map_lapic_id(struct acpi_subtable_header *entry, + u32 acpi_id, int *apic_id) +{ + struct acpi_madt_local_apic *lapic = + (struct acpi_madt_local_apic *)entry; + if ((lapic->lapic_flags & ACPI_MADT_ENABLED) && + lapic->processor_id == acpi_id) { + *apic_id = lapic->id; + return 1; + } + return 0; +} + +static int map_lsapic_id(struct acpi_subtable_header *entry, + u32 acpi_id, int *apic_id) +{ + struct acpi_madt_local_sapic *lsapic = + (struct acpi_madt_local_sapic *)entry; + /* Only check enabled APICs*/ + if (lsapic->lapic_flags & ACPI_MADT_ENABLED) { + /* First check against id */ + if (lsapic->processor_id == acpi_id) { + *apic_id = lsapic->id; + return 1; + /* Check against optional uid */ + } else if (entry->length >= 16 && + lsapic->uid == acpi_id) { + *apic_id = lsapic->uid; + return 1; + } + } + return 0; +} + #ifdef CONFIG_IA64 -#define arch_acpiid_to_apicid ia64_acpiid_to_sapicid #define arch_cpu_to_apicid ia64_cpu_to_sapicid -#define ARCH_BAD_APICID (0xffff) #else -#define arch_acpiid_to_apicid x86_acpiid_to_apicid #define arch_cpu_to_apicid x86_cpu_to_apicid -#define ARCH_BAD_APICID (0xff) #endif -static int convert_acpiid_to_cpu(u8 acpi_id) +static int map_madt_entry(u32 acpi_id) +{ + unsigned long madt_end, entry; + int apic_id = -1; + + if (!madt) + return apic_id; + + entry = (unsigned long)madt; + madt_end = entry + madt->header.length; + + /* Parse all entries looking for a match. */ + + entry += sizeof(struct acpi_table_madt); + while (entry + sizeof(struct acpi_subtable_header) < madt_end) { + struct acpi_subtable_header *header = + (struct acpi_subtable_header *)entry; + if (header->type == ACPI_MADT_TYPE_LOCAL_APIC) { + if (map_lapic_id(header, acpi_id, &apic_id)) + break; + } else if (header->type == ACPI_MADT_TYPE_LOCAL_SAPIC) { + if (map_lsapic_id(header, acpi_id, &apic_id)) + break; + } + entry += header->length; + } + return apic_id; +} + +static int map_mat_entry(acpi_handle handle, u32 acpi_id) +{ + struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; + union acpi_object *obj; + struct acpi_subtable_header *header; + int apic_id = -1; + + if (ACPI_FAILURE(acpi_evaluate_object(handle, "_MAT", NULL, &buffer))) + goto exit; + + if (!buffer.length || !buffer.pointer) + goto exit; + + obj = buffer.pointer; + if (obj->type != ACPI_TYPE_BUFFER || + obj->buffer.length < sizeof(struct acpi_subtable_header)) { + goto exit; + } + + header = (struct acpi_subtable_header *)obj->buffer.pointer; + if (header->type == ACPI_MADT_TYPE_LOCAL_APIC) { + map_lapic_id(header, acpi_id, &apic_id); + } else if (header->type == ACPI_MADT_TYPE_LOCAL_SAPIC) { + map_lsapic_id(header, acpi_id, &apic_id); + } + +exit: + if (buffer.pointer) + kfree(buffer.pointer); + return apic_id; +} + +static int get_apic_id(acpi_handle handle, u32 acpi_id) { - u16 apic_id; int i; + int apic_id = -1; - apic_id = arch_acpiid_to_apicid[acpi_id]; - if (apic_id == ARCH_BAD_APICID) - return -1; + apic_id = map_mat_entry(handle, acpi_id); + if (apic_id == -1) + apic_id = map_madt_entry(acpi_id); + if (apic_id == -1) + return apic_id; - for (i = 0; i < NR_CPUS; i++) { + for (i = 0; i < NR_CPUS; ++i) { if (arch_cpu_to_apicid[i] == apic_id) return i; } @@ -456,7 +552,7 @@ static int acpi_processor_get_info(struct acpi_processor *pr) */ pr->acpi_id = object.processor.proc_id; - cpu_index = convert_acpiid_to_cpu(pr->acpi_id); + cpu_index = get_apic_id(pr->handle, pr->acpi_id); /* Handle UP system running SMP kernel, with no LAPIC in MADT */ if (!cpu0_initialized && (cpu_index == -1) && @@ -473,7 +569,7 @@ static int acpi_processor_get_info(struct acpi_processor *pr) * less than the max # of CPUs. They should be ignored _iff * they are physically not present. */ - if (cpu_index == -1) { + if (pr->id == -1) { if (ACPI_FAILURE (acpi_processor_hotadd_init(pr->handle, &pr->id))) { return -ENODEV; @@ -895,6 +991,12 @@ static int __init acpi_processor_init(void) memset(&processors, 0, sizeof(processors)); memset(&errata, 0, sizeof(errata)); +#ifdef CONFIG_SMP + if (ACPI_FAILURE(acpi_get_table(ACPI_SIG_MADT, 0, + (struct acpi_table_header **)&madt))) + madt = 0; +#endif + acpi_processor_dir = proc_mkdir(ACPI_PROCESSOR_CLASS, acpi_root_dir); if (!acpi_processor_dir) return -ENOMEM; diff --git a/include/asm-i386/acpi.h b/include/asm-i386/acpi.h index 0fb0c01..5e657eb 100644 --- a/include/asm-i386/acpi.h +++ b/include/asm-i386/acpi.h @@ -39,7 +39,7 @@ * Calling conventions: * * ACPI_SYSTEM_XFACE - Interfaces to host OS (handlers, threads) - * ACPI_EXTERNAL_XFACE - External ACPI interfaces + * ACPI_EXTERNAL_XFACE - External ACPI interfaces * ACPI_INTERNAL_XFACE - Internal ACPI interfaces * ACPI_INTERNAL_VAR_XFACE - Internal variable-parameter list interfaces */ @@ -87,7 +87,7 @@ extern void check_acpi_pci(void); static inline void check_acpi_pci(void) { } #endif -#ifdef CONFIG_ACPI +#ifdef CONFIG_ACPI extern int acpi_lapic; extern int acpi_ioapic; extern int acpi_noirq; @@ -95,9 +95,9 @@ extern int acpi_strict; extern int acpi_disabled; extern int acpi_ht; extern int acpi_pci_disabled; -static inline void disable_acpi(void) -{ - acpi_disabled = 1; +static inline void disable_acpi(void) +{ + acpi_disabled = 1; acpi_ht = 0; acpi_pci_disabled = 1; acpi_noirq = 1; @@ -114,9 +114,9 @@ extern int acpi_use_timer_override; #endif static inline void acpi_noirq_set(void) { acpi_noirq = 1; } -static inline void acpi_disable_pci(void) +static inline void acpi_disable_pci(void) { - acpi_pci_disabled = 1; + acpi_pci_disabled = 1; acpi_noirq_set(); } extern int acpi_irq_balance_set(char *str); @@ -144,8 +144,6 @@ extern void acpi_reserve_bootmem(void); #endif /*CONFIG_ACPI_SLEEP*/ -extern u8 x86_acpiid_to_apicid[]; - #define ARCH_HAS_POWER_INIT 1 #endif /*__KERNEL__*/ diff --git a/include/asm-ia64/acpi.h b/include/asm-ia64/acpi.h index dba34d5..5d03792 100644 --- a/include/asm-ia64/acpi.h +++ b/include/asm-ia64/acpi.h @@ -119,8 +119,6 @@ extern int __devinitdata pxm_to_nid_map[MAX_PXM_DOMAINS]; extern int __initdata nid_to_pxm_map[MAX_NUMNODES]; #endif -extern u16 ia64_acpiid_to_sapicid[]; - /* * Refer Intel ACPI _PDC support document for bit definitions */ diff --git a/include/asm-x86_64/acpi.h b/include/asm-x86_64/acpi.h index 49f92f3..a29f050 100644 --- a/include/asm-x86_64/acpi.h +++ b/include/asm-x86_64/acpi.h @@ -37,7 +37,7 @@ * Calling conventions: * * ACPI_SYSTEM_XFACE - Interfaces to host OS (handlers, threads) - * ACPI_EXTERNAL_XFACE - External ACPI interfaces + * ACPI_EXTERNAL_XFACE - External ACPI interfaces * ACPI_INTERNAL_XFACE - Internal ACPI interfaces * ACPI_INTERNAL_VAR_XFACE - Internal variable-parameter list interfaces */ @@ -87,10 +87,10 @@ extern int acpi_strict; extern int acpi_disabled; extern int acpi_pci_disabled; extern int acpi_ht; -static inline void disable_acpi(void) -{ - acpi_disabled = 1; - acpi_ht = 0; +static inline void disable_acpi(void) +{ + acpi_disabled = 1; + acpi_ht = 0; acpi_pci_disabled = 1; acpi_noirq = 1; } @@ -100,9 +100,9 @@ static inline void disable_acpi(void) extern int acpi_gsi_to_irq(u32 gsi, unsigned int *irq); static inline void acpi_noirq_set(void) { acpi_noirq = 1; } -static inline void acpi_disable_pci(void) +static inline void acpi_disable_pci(void) { - acpi_pci_disabled = 1; + acpi_pci_disabled = 1; acpi_noirq_set(); } extern int acpi_irq_balance_set(char *str); @@ -136,8 +136,6 @@ extern void acpi_reserve_bootmem(void); extern int acpi_disabled; extern int acpi_pci_disabled; -extern u8 x86_acpiid_to_apicid[]; - #define ARCH_HAS_POWER_INIT 1 extern int acpi_skip_timer_override; -- cgit v0.10.2 From 11bf04c44fd284a5f4e2348a04da6f749cace250 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 19:48:23 +0300 Subject: ACPICA: Allow processor to be declared with the Device() instead of Processor() Allow processor to be declered with the Device(), such as: Device(CPU1234) { Name(_HID, "ACPI007") Name(_UID, 1234) } Signed-off-by: Len Brown diff --git a/drivers/acpi/processor_core.c b/drivers/acpi/processor_core.c index 6893c0b..eacf9a2 100644 --- a/drivers/acpi/processor_core.c +++ b/drivers/acpi/processor_core.c @@ -377,7 +377,7 @@ static int acpi_processor_remove_fs(struct acpi_device *device) /* Use the acpiid in MADT to map cpus in case of SMP */ #ifndef CONFIG_SMP -#define convert_acpiid_to_cpu(acpi_id) (-1) +static int get_cpu_id(acpi_handle handle, u32 acpi_id) {return -1;} #else static struct acpi_table_madt *madt; @@ -483,7 +483,7 @@ exit: return apic_id; } -static int get_apic_id(acpi_handle handle, u32 acpi_id) +static int get_cpu_id(acpi_handle handle, u32 acpi_id) { int i; int apic_id = -1; @@ -506,7 +506,7 @@ static int get_apic_id(acpi_handle handle, u32 acpi_id) Driver Interface -------------------------------------------------------------------------- */ -static int acpi_processor_get_info(struct acpi_processor *pr) +static int acpi_processor_get_info(struct acpi_processor *pr, unsigned has_uid) { acpi_status status = 0; union acpi_object object = { 0 }; @@ -535,24 +535,35 @@ static int acpi_processor_get_info(struct acpi_processor *pr) ACPI_DEBUG_PRINT((ACPI_DB_INFO, "No bus mastering arbitration control\n")); - /* - * Evalute the processor object. Note that it is common on SMP to - * have the first (boot) processor with a valid PBLK address while - * all others have a NULL address. - */ - status = acpi_evaluate_object(pr->handle, NULL, NULL, &buffer); - if (ACPI_FAILURE(status)) { - printk(KERN_ERR PREFIX "Evaluating processor object\n"); - return -ENODEV; - } - - /* - * TBD: Synch processor ID (via LAPIC/LSAPIC structures) on SMP. - * >>> 'acpi_get_processor_id(acpi_id, &id)' in arch/xxx/acpi.c - */ - pr->acpi_id = object.processor.proc_id; + /* Check if it is a Device with HID and UID */ + if (has_uid) { + unsigned long value; + status = acpi_evaluate_integer(pr->handle, METHOD_NAME__UID, + NULL, &value); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR PREFIX "Evaluating processor _UID\n"); + return -ENODEV; + } + pr->acpi_id = value; + } else { + /* + * Evalute the processor object. Note that it is common on SMP to + * have the first (boot) processor with a valid PBLK address while + * all others have a NULL address. + */ + status = acpi_evaluate_object(pr->handle, NULL, NULL, &buffer); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR PREFIX "Evaluating processor object\n"); + return -ENODEV; + } - cpu_index = get_apic_id(pr->handle, pr->acpi_id); + /* + * TBD: Synch processor ID (via LAPIC/LSAPIC structures) on SMP. + * >>> 'acpi_get_processor_id(acpi_id, &id)' in arch/xxx/acpi.c + */ + pr->acpi_id = object.processor.proc_id; + } + cpu_index = get_cpu_id(pr->handle, pr->acpi_id); /* Handle UP system running SMP kernel, with no LAPIC in MADT */ if (!cpu0_initialized && (cpu_index == -1) && @@ -621,7 +632,7 @@ static int __cpuinit acpi_processor_start(struct acpi_device *device) pr = acpi_driver_data(device); - result = acpi_processor_get_info(pr); + result = acpi_processor_get_info(pr, device->flags.unique_id); if (result) { /* Processor is physically not present */ return 0; diff --git a/include/acpi/acpi_drivers.h b/include/acpi/acpi_drivers.h index 6a5bdce..baaa734 100644 --- a/include/acpi/acpi_drivers.h +++ b/include/acpi/acpi_drivers.h @@ -37,7 +37,7 @@ /* _HID definitions */ #define ACPI_POWER_HID "ACPI_PWR" -#define ACPI_PROCESSOR_HID "ACPI_CPU" +#define ACPI_PROCESSOR_HID "ACPI0007" #define ACPI_SYSTEM_HID "ACPI_SYS" #define ACPI_THERMAL_HID "ACPI_THM" #define ACPI_BUTTON_HID_POWERF "ACPI_FPB" -- cgit v0.10.2 From 6c9deb7201d96733dcd1b4cc44e99232308db359 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:24 +0300 Subject: ACPICA: Update copyright to 2007. Added 2007 copyright to all module headers and signons. This affects virtually every file in the ACPICA core subsystem, iASL compiler, and the utilities. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/dispatcher/dsfield.c b/drivers/acpi/dispatcher/dsfield.c index 379dd71..f049639 100644 --- a/drivers/acpi/dispatcher/dsfield.c +++ b/drivers/acpi/dispatcher/dsfield.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dsinit.c b/drivers/acpi/dispatcher/dsinit.c index 9db09de..af923c3 100644 --- a/drivers/acpi/dispatcher/dsinit.c +++ b/drivers/acpi/dispatcher/dsinit.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dsmethod.c b/drivers/acpi/dispatcher/dsmethod.c index 57c5159..1cbe619 100644 --- a/drivers/acpi/dispatcher/dsmethod.c +++ b/drivers/acpi/dispatcher/dsmethod.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dsmthdat.c b/drivers/acpi/dispatcher/dsmthdat.c index 459160f..ba4626e 100644 --- a/drivers/acpi/dispatcher/dsmthdat.c +++ b/drivers/acpi/dispatcher/dsmthdat.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dsobject.c b/drivers/acpi/dispatcher/dsobject.c index f9f6862b..a474ca2 100644 --- a/drivers/acpi/dispatcher/dsobject.c +++ b/drivers/acpi/dispatcher/dsobject.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dsopcode.c b/drivers/acpi/dispatcher/dsopcode.c index 26035a3..6c6104a 100644 --- a/drivers/acpi/dispatcher/dsopcode.c +++ b/drivers/acpi/dispatcher/dsopcode.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dsutils.c b/drivers/acpi/dispatcher/dsutils.c index 05230ba..e4073e0 100644 --- a/drivers/acpi/dispatcher/dsutils.c +++ b/drivers/acpi/dispatcher/dsutils.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dswexec.c b/drivers/acpi/dispatcher/dswexec.c index b5b8f16..69693fa 100644 --- a/drivers/acpi/dispatcher/dswexec.c +++ b/drivers/acpi/dispatcher/dswexec.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dswload.c b/drivers/acpi/dispatcher/dswload.c index baf04e8..8ab9d1b 100644 --- a/drivers/acpi/dispatcher/dswload.c +++ b/drivers/acpi/dispatcher/dswload.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dswscope.c b/drivers/acpi/dispatcher/dswscope.c index c922897..3927c49 100644 --- a/drivers/acpi/dispatcher/dswscope.c +++ b/drivers/acpi/dispatcher/dswscope.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/dispatcher/dswstate.c b/drivers/acpi/dispatcher/dswstate.c index 7817e55..16c8e38 100644 --- a/drivers/acpi/dispatcher/dswstate.c +++ b/drivers/acpi/dispatcher/dswstate.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evevent.c b/drivers/acpi/events/evevent.c index f09d1aa..a1f87b5 100644 --- a/drivers/acpi/events/evevent.c +++ b/drivers/acpi/events/evevent.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evgpe.c b/drivers/acpi/events/evgpe.c index 35933be..dfac3ec 100644 --- a/drivers/acpi/events/evgpe.c +++ b/drivers/acpi/events/evgpe.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evgpeblk.c b/drivers/acpi/events/evgpeblk.c index a23634c..ad5bc76 100644 --- a/drivers/acpi/events/evgpeblk.c +++ b/drivers/acpi/events/evgpeblk.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evmisc.c b/drivers/acpi/events/evmisc.c index db16300..1b784ffe 100644 --- a/drivers/acpi/events/evmisc.c +++ b/drivers/acpi/events/evmisc.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evregion.c b/drivers/acpi/events/evregion.c index ef45971..e99f0c4 100644 --- a/drivers/acpi/events/evregion.c +++ b/drivers/acpi/events/evregion.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evrgnini.c b/drivers/acpi/events/evrgnini.c index 6176602..a4fa7e6 100644 --- a/drivers/acpi/events/evrgnini.c +++ b/drivers/acpi/events/evrgnini.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evsci.c b/drivers/acpi/events/evsci.c index d7680ac..7e5d15c 100644 --- a/drivers/acpi/events/evsci.c +++ b/drivers/acpi/events/evsci.c @@ -6,7 +6,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evxface.c b/drivers/acpi/events/evxface.c index a2af48e..685a103 100644 --- a/drivers/acpi/events/evxface.c +++ b/drivers/acpi/events/evxface.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evxfevnt.c b/drivers/acpi/events/evxfevnt.c index bbd631d..17065e9 100644 --- a/drivers/acpi/events/evxfevnt.c +++ b/drivers/acpi/events/evxfevnt.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/events/evxfregn.c b/drivers/acpi/events/evxfregn.c index 83b12a9..7bf09c5 100644 --- a/drivers/acpi/events/evxfregn.c +++ b/drivers/acpi/events/evxfregn.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exconfig.c b/drivers/acpi/executer/exconfig.c index 61ec855..25802f3 100644 --- a/drivers/acpi/executer/exconfig.c +++ b/drivers/acpi/executer/exconfig.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exconvrt.c b/drivers/acpi/executer/exconvrt.c index 544e81a..d470e8b 100644 --- a/drivers/acpi/executer/exconvrt.c +++ b/drivers/acpi/executer/exconvrt.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/excreate.c b/drivers/acpi/executer/excreate.c index c665aa7..7c38528 100644 --- a/drivers/acpi/executer/excreate.c +++ b/drivers/acpi/executer/excreate.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exdump.c b/drivers/acpi/executer/exdump.c index c9cab16..68d283f 100644 --- a/drivers/acpi/executer/exdump.c +++ b/drivers/acpi/executer/exdump.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exfield.c b/drivers/acpi/executer/exfield.c index 9ea9c3a..2d88a3d 100644 --- a/drivers/acpi/executer/exfield.c +++ b/drivers/acpi/executer/exfield.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exfldio.c b/drivers/acpi/executer/exfldio.c index b3f30d8..65a48b6 100644 --- a/drivers/acpi/executer/exfldio.c +++ b/drivers/acpi/executer/exfldio.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exmisc.c b/drivers/acpi/executer/exmisc.c index bd98aab..f13d1ce 100644 --- a/drivers/acpi/executer/exmisc.c +++ b/drivers/acpi/executer/exmisc.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exmutex.c b/drivers/acpi/executer/exmutex.c index b0be2f4..5101bad 100644 --- a/drivers/acpi/executer/exmutex.c +++ b/drivers/acpi/executer/exmutex.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exnames.c b/drivers/acpi/executer/exnames.c index d3d7036..1ee4fb1 100644 --- a/drivers/acpi/executer/exnames.c +++ b/drivers/acpi/executer/exnames.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exoparg1.c b/drivers/acpi/executer/exoparg1.c index 6f2e69c..252f10a 100644 --- a/drivers/acpi/executer/exoparg1.c +++ b/drivers/acpi/executer/exoparg1.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exoparg2.c b/drivers/acpi/executer/exoparg2.c index 7d2cbc1..17e652e 100644 --- a/drivers/acpi/executer/exoparg2.c +++ b/drivers/acpi/executer/exoparg2.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exoparg3.c b/drivers/acpi/executer/exoparg3.c index e2d945d..7fe67cf 100644 --- a/drivers/acpi/executer/exoparg3.c +++ b/drivers/acpi/executer/exoparg3.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exoparg6.c b/drivers/acpi/executer/exoparg6.c index f0c0ba6..bd80a9c 100644 --- a/drivers/acpi/executer/exoparg6.c +++ b/drivers/acpi/executer/exoparg6.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exprep.c b/drivers/acpi/executer/exprep.c index 44d064f..a669662 100644 --- a/drivers/acpi/executer/exprep.c +++ b/drivers/acpi/executer/exprep.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exregion.c b/drivers/acpi/executer/exregion.c index c6819e0..2e9ce94 100644 --- a/drivers/acpi/executer/exregion.c +++ b/drivers/acpi/executer/exregion.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exresnte.c b/drivers/acpi/executer/exresnte.c index 3089b05..2b3a01c 100644 --- a/drivers/acpi/executer/exresnte.c +++ b/drivers/acpi/executer/exresnte.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exresolv.c b/drivers/acpi/executer/exresolv.c index fa17f55..6c64e55 100644 --- a/drivers/acpi/executer/exresolv.c +++ b/drivers/acpi/executer/exresolv.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exresop.c b/drivers/acpi/executer/exresop.c index 411d120..ba76186 100644 --- a/drivers/acpi/executer/exresop.c +++ b/drivers/acpi/executer/exresop.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exstore.c b/drivers/acpi/executer/exstore.c index 0456405..f4b69a6 100644 --- a/drivers/acpi/executer/exstore.c +++ b/drivers/acpi/executer/exstore.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exstoren.c b/drivers/acpi/executer/exstoren.c index 591aaf0..1d622c6 100644 --- a/drivers/acpi/executer/exstoren.c +++ b/drivers/acpi/executer/exstoren.c @@ -7,7 +7,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exstorob.c b/drivers/acpi/executer/exstorob.c index 99ebe5a..8233d40 100644 --- a/drivers/acpi/executer/exstorob.c +++ b/drivers/acpi/executer/exstorob.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exsystem.c b/drivers/acpi/executer/exsystem.c index 7e5aeb1..9460baf 100644 --- a/drivers/acpi/executer/exsystem.c +++ b/drivers/acpi/executer/exsystem.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/executer/exutils.c b/drivers/acpi/executer/exutils.c index e32d489..6b0aecc 100644 --- a/drivers/acpi/executer/exutils.c +++ b/drivers/acpi/executer/exutils.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/hardware/hwacpi.c b/drivers/acpi/hardware/hwacpi.c index dbcc4c0..6031ca1 100644 --- a/drivers/acpi/hardware/hwacpi.c +++ b/drivers/acpi/hardware/hwacpi.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/hardware/hwgpe.c b/drivers/acpi/hardware/hwgpe.c index 3d548b5..117a05c 100644 --- a/drivers/acpi/hardware/hwgpe.c +++ b/drivers/acpi/hardware/hwgpe.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/hardware/hwregs.c b/drivers/acpi/hardware/hwregs.c index 5b19fc7..1d371fa 100644 --- a/drivers/acpi/hardware/hwregs.c +++ b/drivers/acpi/hardware/hwregs.c @@ -7,7 +7,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/hardware/hwsleep.c b/drivers/acpi/hardware/hwsleep.c index 7c96451..57901ca 100644 --- a/drivers/acpi/hardware/hwsleep.c +++ b/drivers/acpi/hardware/hwsleep.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/hardware/hwtimer.c b/drivers/acpi/hardware/hwtimer.c index abd86e8d..c32eab6 100644 --- a/drivers/acpi/hardware/hwtimer.c +++ b/drivers/acpi/hardware/hwtimer.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsaccess.c b/drivers/acpi/namespace/nsaccess.c index 2529ae9..57faf59 100644 --- a/drivers/acpi/namespace/nsaccess.c +++ b/drivers/acpi/namespace/nsaccess.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsalloc.c b/drivers/acpi/namespace/nsalloc.c index 1e6a1b0..1d693d8 100644 --- a/drivers/acpi/namespace/nsalloc.c +++ b/drivers/acpi/namespace/nsalloc.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsdump.c b/drivers/acpi/namespace/nsdump.c index ec5ce59..1fc4f86 100644 --- a/drivers/acpi/namespace/nsdump.c +++ b/drivers/acpi/namespace/nsdump.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsdumpdv.c b/drivers/acpi/namespace/nsdumpdv.c index c6bf5d3..5097e16 100644 --- a/drivers/acpi/namespace/nsdumpdv.c +++ b/drivers/acpi/namespace/nsdumpdv.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nseval.c b/drivers/acpi/namespace/nseval.c index 7156616..aa6370c 100644 --- a/drivers/acpi/namespace/nseval.c +++ b/drivers/acpi/namespace/nseval.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsinit.c b/drivers/acpi/namespace/nsinit.c index 0d3a42b..326af8f 100644 --- a/drivers/acpi/namespace/nsinit.c +++ b/drivers/acpi/namespace/nsinit.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsload.c b/drivers/acpi/namespace/nsload.c index 5d555f8..d4f9654 100644 --- a/drivers/acpi/namespace/nsload.c +++ b/drivers/acpi/namespace/nsload.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsnames.c b/drivers/acpi/namespace/nsnames.c index 97b8332..cbd94af 100644 --- a/drivers/acpi/namespace/nsnames.c +++ b/drivers/acpi/namespace/nsnames.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsobject.c b/drivers/acpi/namespace/nsobject.c index aabe879..d9d7377 100644 --- a/drivers/acpi/namespace/nsobject.c +++ b/drivers/acpi/namespace/nsobject.c @@ -6,7 +6,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsparse.c b/drivers/acpi/namespace/nsparse.c index a68de26..0e57cc6 100644 --- a/drivers/acpi/namespace/nsparse.c +++ b/drivers/acpi/namespace/nsparse.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nssearch.c b/drivers/acpi/namespace/nssearch.c index d261c9b..e863be6 100644 --- a/drivers/acpi/namespace/nssearch.c +++ b/drivers/acpi/namespace/nssearch.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsutils.c b/drivers/acpi/namespace/nsutils.c index 4eb155c..90fd059 100644 --- a/drivers/acpi/namespace/nsutils.c +++ b/drivers/acpi/namespace/nsutils.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nswalk.c b/drivers/acpi/namespace/nswalk.c index bccf27d..94eb8f3 100644 --- a/drivers/acpi/namespace/nswalk.c +++ b/drivers/acpi/namespace/nswalk.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsxfeval.c b/drivers/acpi/namespace/nsxfeval.c index 6a0a46e..7ac6ace 100644 --- a/drivers/acpi/namespace/nsxfeval.c +++ b/drivers/acpi/namespace/nsxfeval.c @@ -6,7 +6,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsxfname.c b/drivers/acpi/namespace/nsxfname.c index 408bd11..b489781 100644 --- a/drivers/acpi/namespace/nsxfname.c +++ b/drivers/acpi/namespace/nsxfname.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/namespace/nsxfobj.c b/drivers/acpi/namespace/nsxfobj.c index a18b1c2..faa3758 100644 --- a/drivers/acpi/namespace/nsxfobj.c +++ b/drivers/acpi/namespace/nsxfobj.c @@ -6,7 +6,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/psargs.c b/drivers/acpi/parser/psargs.c index bf88e07..c2b9835 100644 --- a/drivers/acpi/parser/psargs.c +++ b/drivers/acpi/parser/psargs.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/psloop.c b/drivers/acpi/parser/psloop.c index 881687c..773aee8 100644 --- a/drivers/acpi/parser/psloop.c +++ b/drivers/acpi/parser/psloop.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/psopcode.c b/drivers/acpi/parser/psopcode.c index 4bd25e3..16d8b6c 100644 --- a/drivers/acpi/parser/psopcode.c +++ b/drivers/acpi/parser/psopcode.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/psparse.c b/drivers/acpi/parser/psparse.c index 6e875ce..5d63f48 100644 --- a/drivers/acpi/parser/psparse.c +++ b/drivers/acpi/parser/psparse.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/psscope.c b/drivers/acpi/parser/psscope.c index a3e0314d..77cfa4e 100644 --- a/drivers/acpi/parser/psscope.c +++ b/drivers/acpi/parser/psscope.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/pstree.c b/drivers/acpi/parser/pstree.c index 0015717..966e7ea 100644 --- a/drivers/acpi/parser/pstree.c +++ b/drivers/acpi/parser/pstree.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/psutils.c b/drivers/acpi/parser/psutils.c index d405387..8ca5200 100644 --- a/drivers/acpi/parser/psutils.c +++ b/drivers/acpi/parser/psutils.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/pswalk.c b/drivers/acpi/parser/pswalk.c index a84a547..49f9757 100644 --- a/drivers/acpi/parser/pswalk.c +++ b/drivers/acpi/parser/pswalk.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/parser/psxface.c b/drivers/acpi/parser/psxface.c index fc5b3e5..94103bc 100644 --- a/drivers/acpi/parser/psxface.c +++ b/drivers/acpi/parser/psxface.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsaddr.c b/drivers/acpi/resources/rsaddr.c index 8fa3213..271e615 100644 --- a/drivers/acpi/resources/rsaddr.c +++ b/drivers/acpi/resources/rsaddr.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rscalc.c b/drivers/acpi/resources/rscalc.c index cf87b02..8c6d3fd 100644 --- a/drivers/acpi/resources/rscalc.c +++ b/drivers/acpi/resources/rscalc.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rscreate.c b/drivers/acpi/resources/rscreate.c index 008058a..1358c06 100644 --- a/drivers/acpi/resources/rscreate.c +++ b/drivers/acpi/resources/rscreate.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsdump.c b/drivers/acpi/resources/rsdump.c index 9c99a72..de20a5d 100644 --- a/drivers/acpi/resources/rsdump.c +++ b/drivers/acpi/resources/rsdump.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsinfo.c b/drivers/acpi/resources/rsinfo.c index 9e7ae2f..7e3c335 100644 --- a/drivers/acpi/resources/rsinfo.c +++ b/drivers/acpi/resources/rsinfo.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsio.c b/drivers/acpi/resources/rsio.c index ea56716..b297bc3 100644 --- a/drivers/acpi/resources/rsio.c +++ b/drivers/acpi/resources/rsio.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsirq.c b/drivers/acpi/resources/rsirq.c index 1fa63bc..5657f7b 100644 --- a/drivers/acpi/resources/rsirq.c +++ b/drivers/acpi/resources/rsirq.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rslist.c b/drivers/acpi/resources/rslist.c index 29423ce..a92755c 100644 --- a/drivers/acpi/resources/rslist.c +++ b/drivers/acpi/resources/rslist.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsmemory.c b/drivers/acpi/resources/rsmemory.c index a513193..521eab7 100644 --- a/drivers/acpi/resources/rsmemory.c +++ b/drivers/acpi/resources/rsmemory.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsmisc.c b/drivers/acpi/resources/rsmisc.c index faf6e10..3b63b56 100644 --- a/drivers/acpi/resources/rsmisc.c +++ b/drivers/acpi/resources/rsmisc.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsutils.c b/drivers/acpi/resources/rsutils.c index a9cbee8..2442a8f 100644 --- a/drivers/acpi/resources/rsutils.c +++ b/drivers/acpi/resources/rsutils.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/resources/rsxface.c b/drivers/acpi/resources/rsxface.c index 1999e2a..991f890 100644 --- a/drivers/acpi/resources/rsxface.c +++ b/drivers/acpi/resources/rsxface.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c index 31a4a00..273b5fd 100644 --- a/drivers/acpi/tables/tbfadt.c +++ b/drivers/acpi/tables/tbfadt.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/tables/tbfind.c b/drivers/acpi/tables/tbfind.c index 769213c..058c064 100644 --- a/drivers/acpi/tables/tbfind.c +++ b/drivers/acpi/tables/tbfind.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/tables/tbinstal.c b/drivers/acpi/tables/tbinstal.c index b07d9c8..0e7b121 100644 --- a/drivers/acpi/tables/tbinstal.c +++ b/drivers/acpi/tables/tbinstal.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 0874ab2..4a2f99e 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 77224bd..84a8089 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/tables/tbxfroot.c b/drivers/acpi/tables/tbxfroot.c index 82c0b66..cf8fa51 100644 --- a/drivers/acpi/tables/tbxfroot.c +++ b/drivers/acpi/tables/tbxfroot.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utalloc.c b/drivers/acpi/utilities/utalloc.c index b716797..55a7648 100644 --- a/drivers/acpi/utilities/utalloc.c +++ b/drivers/acpi/utilities/utalloc.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utcache.c b/drivers/acpi/utilities/utcache.c index d796fca..870f6ed 100644 --- a/drivers/acpi/utilities/utcache.c +++ b/drivers/acpi/utilities/utcache.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utcopy.c b/drivers/acpi/utilities/utcopy.c index 5c38276..84d529db 100644 --- a/drivers/acpi/utilities/utcopy.c +++ b/drivers/acpi/utilities/utcopy.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utdebug.c b/drivers/acpi/utilities/utdebug.c index 8ba8624..179ad18 100644 --- a/drivers/acpi/utilities/utdebug.c +++ b/drivers/acpi/utilities/utdebug.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utdelete.c b/drivers/acpi/utilities/utdelete.c index af8e65f..f777ceb 100644 --- a/drivers/acpi/utilities/utdelete.c +++ b/drivers/acpi/utilities/utdelete.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/uteval.c b/drivers/acpi/utilities/uteval.c index d6d7121..13d5879 100644 --- a/drivers/acpi/utilities/uteval.c +++ b/drivers/acpi/utilities/uteval.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utglobal.c b/drivers/acpi/utilities/utglobal.c index 62929f4..af33358 100644 --- a/drivers/acpi/utilities/utglobal.c +++ b/drivers/acpi/utilities/utglobal.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utinit.c b/drivers/acpi/utilities/utinit.c index 303bde70..ad3c0d0 100644 --- a/drivers/acpi/utilities/utinit.c +++ b/drivers/acpi/utilities/utinit.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utmath.c b/drivers/acpi/utilities/utmath.c index 19d74be..0c56a0d 100644 --- a/drivers/acpi/utilities/utmath.c +++ b/drivers/acpi/utilities/utmath.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utmisc.c b/drivers/acpi/utilities/utmisc.c index e437bc7..50133ff 100644 --- a/drivers/acpi/utilities/utmisc.c +++ b/drivers/acpi/utilities/utmisc.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utmutex.c b/drivers/acpi/utilities/utmutex.c index 180e73c..cbad2ef 100644 --- a/drivers/acpi/utilities/utmutex.c +++ b/drivers/acpi/utilities/utmutex.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utobject.c b/drivers/acpi/utilities/utobject.c index ba7d8ac..4696124 100644 --- a/drivers/acpi/utilities/utobject.c +++ b/drivers/acpi/utilities/utobject.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utresrc.c b/drivers/acpi/utilities/utresrc.c index 5a2de92..e8fe1ba 100644 --- a/drivers/acpi/utilities/utresrc.c +++ b/drivers/acpi/utilities/utresrc.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utstate.c b/drivers/acpi/utilities/utstate.c index eaa13d0..edcaafa 100644 --- a/drivers/acpi/utilities/utstate.c +++ b/drivers/acpi/utilities/utstate.c @@ -5,7 +5,7 @@ ******************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/drivers/acpi/utilities/utxface.c b/drivers/acpi/utilities/utxface.c index 0a3202d..de3276f 100644 --- a/drivers/acpi/utilities/utxface.c +++ b/drivers/acpi/utilities/utxface.c @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index aaa2813..ade404f 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acdebug.h b/include/acpi/acdebug.h index c46a33a..d626bb1 100644 --- a/include/acpi/acdebug.h +++ b/include/acpi/acdebug.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acdisasm.h b/include/acpi/acdisasm.h index ea35f1f..389d772 100644 --- a/include/acpi/acdisasm.h +++ b/include/acpi/acdisasm.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acdispat.h b/include/acpi/acdispat.h index f0272d4..cb8d286 100644 --- a/include/acpi/acdispat.h +++ b/include/acpi/acdispat.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acevents.h b/include/acpi/acevents.h index 23414282..d23cdf3 100644 --- a/include/acpi/acevents.h +++ b/include/acpi/acevents.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acexcep.h b/include/acpi/acexcep.h index 8fa00e8..b73f18a 100644 --- a/include/acpi/acexcep.h +++ b/include/acpi/acexcep.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acglobal.h b/include/acpi/acglobal.h index 5b5d437..24c3f05 100644 --- a/include/acpi/acglobal.h +++ b/include/acpi/acglobal.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/achware.h b/include/acpi/achware.h index ae449f2..9df275c 100644 --- a/include/acpi/achware.h +++ b/include/acpi/achware.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acinterp.h b/include/acpi/acinterp.h index 8aebe57..ce7c9d6 100644 --- a/include/acpi/acinterp.h +++ b/include/acpi/acinterp.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/aclocal.h b/include/acpi/aclocal.h index e135dab..6f83ddb 100644 --- a/include/acpi/aclocal.h +++ b/include/acpi/aclocal.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acmacros.h b/include/acpi/acmacros.h index 549e533..8948a64 100644 --- a/include/acpi/acmacros.h +++ b/include/acpi/acmacros.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acnames.h b/include/acpi/acnames.h index b67da36..34bfae8 100644 --- a/include/acpi/acnames.h +++ b/include/acpi/acnames.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acnamesp.h b/include/acpi/acnamesp.h index 19a6129..535b7e1 100644 --- a/include/acpi/acnamesp.h +++ b/include/acpi/acnamesp.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acobject.h b/include/acpi/acobject.h index b81e923..04e9735 100644 --- a/include/acpi/acobject.h +++ b/include/acpi/acobject.h @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acopcode.h b/include/acpi/acopcode.h index d71f5d9..e6f76a2 100644 --- a/include/acpi/acopcode.h +++ b/include/acpi/acopcode.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acoutput.h b/include/acpi/acoutput.h index 8d5039d..7812267 100644 --- a/include/acpi/acoutput.h +++ b/include/acpi/acoutput.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acparser.h b/include/acpi/acparser.h index 9d49d3c..85c358e 100644 --- a/include/acpi/acparser.h +++ b/include/acpi/acparser.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acpi.h b/include/acpi/acpi.h index b9a39d1..2e5f00d 100644 --- a/include/acpi/acpi.h +++ b/include/acpi/acpi.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acpiosxf.h b/include/acpi/acpiosxf.h index 9a5ffcf..781394b 100644 --- a/include/acpi/acpiosxf.h +++ b/include/acpi/acpiosxf.h @@ -8,7 +8,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acpixf.h b/include/acpi/acpixf.h index 918280e..e08f7df 100644 --- a/include/acpi/acpixf.h +++ b/include/acpi/acpixf.h @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acresrc.h b/include/acpi/acresrc.h index 80a3b33..9486ab2 100644 --- a/include/acpi/acresrc.h +++ b/include/acpi/acresrc.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acstruct.h b/include/acpi/acstruct.h index 9c800b6..aeb4498 100644 --- a/include/acpi/acstruct.h +++ b/include/acpi/acstruct.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/actables.h b/include/acpi/actables.h index e7efb8a..2b9f46f 100644 --- a/include/acpi/actables.h +++ b/include/acpi/actables.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/actbl.h b/include/acpi/actbl.h index d6af14e..09469e7 100644 --- a/include/acpi/actbl.h +++ b/include/acpi/actbl.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/actbl1.h b/include/acpi/actbl1.h index b7178eb..4e5d3ca 100644 --- a/include/acpi/actbl1.h +++ b/include/acpi/actbl1.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/actypes.h b/include/acpi/actypes.h index ee1a118..72a6e2c 100644 --- a/include/acpi/actypes.h +++ b/include/acpi/actypes.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/acutils.h b/include/acpi/acutils.h index ba7d7e9..883ffe9 100644 --- a/include/acpi/acutils.h +++ b/include/acpi/acutils.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/amlcode.h b/include/acpi/amlcode.h index fd0c722..da53a4e 100644 --- a/include/acpi/amlcode.h +++ b/include/acpi/amlcode.h @@ -7,7 +7,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/amlresrc.h b/include/acpi/amlresrc.h index be03818..f7d5412 100644 --- a/include/acpi/amlresrc.h +++ b/include/acpi/amlresrc.h @@ -6,7 +6,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/platform/acenv.h b/include/acpi/platform/acenv.h index 453a469..dab2ec5 100644 --- a/include/acpi/platform/acenv.h +++ b/include/acpi/platform/acenv.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/platform/acgcc.h b/include/acpi/platform/acgcc.h index da80933..3bb5049 100644 --- a/include/acpi/platform/acgcc.h +++ b/include/acpi/platform/acgcc.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without diff --git a/include/acpi/platform/aclinux.h b/include/acpi/platform/aclinux.h index 7f1e929..5f532d2 100644 --- a/include/acpi/platform/aclinux.h +++ b/include/acpi/platform/aclinux.h @@ -5,7 +5,7 @@ *****************************************************************************/ /* - * Copyright (C) 2000 - 2006, R. Byron Moore + * Copyright (C) 2000 - 2007, R. Byron Moore * All rights reserved. * * Redistribution and use in source and binary forms, with or without -- cgit v0.10.2 From 035f994b3ccfcfc555f838e2f33a2e49721e8533 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:24 +0300 Subject: ACPICA: Fix for incorrect parameter passed to AcpiTbDeleteTable during table load. Bad pointer was passed in the case where the DSDT is overridden. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbxface.c b/drivers/acpi/tables/tbxface.c index 84a8089..807978d 100644 --- a/drivers/acpi/tables/tbxface.c +++ b/drivers/acpi/tables/tbxface.c @@ -524,7 +524,8 @@ static acpi_status acpi_tb_load_namespace(void) /* * DSDT table has been found */ - acpi_tb_delete_table(ACPI_TABLE_INDEX_DSDT); + acpi_tb_delete_table(&acpi_gbl_root_table_list. + tables[ACPI_TABLE_INDEX_DSDT]); acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].pointer = table; acpi_gbl_root_table_list.tables[ACPI_TABLE_INDEX_DSDT].length = -- cgit v0.10.2 From 5763d3c7a0c2b165504954b1eeb898fb8d97d8f5 Mon Sep 17 00:00:00 2001 From: Bob Moore Date: Fri, 2 Feb 2007 19:48:24 +0300 Subject: ACPICA: Update version to 20070126 Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/include/acpi/acconfig.h b/include/acpi/acconfig.h index ade404f..422f29c 100644 --- a/include/acpi/acconfig.h +++ b/include/acpi/acconfig.h @@ -63,7 +63,7 @@ /* Current ACPICA subsystem version in YYYYMMDD format */ -#define ACPI_CA_VERSION 0x20061215 +#define ACPI_CA_VERSION 0x20070126 /* * OS name, used for the _OS object. The _OS object is essentially obsolete, -- cgit v0.10.2 From 0e5683350f5bcd23d5d579f91d488caeda432617 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 21:37:53 -0500 Subject: ACPI: build fix for IBM x440 - CONFIG_X86_SUMMIT i386 srat.c broke due to re-names from ACPICA table-manager re-write. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/arch/i386/kernel/srat.c b/arch/i386/kernel/srat.c index f7e735c..2a8713e 100644 --- a/arch/i386/kernel/srat.c +++ b/arch/i386/kernel/srat.c @@ -62,19 +62,19 @@ extern void * boot_ioremap(unsigned long, unsigned long); /* Identify CPU proximity domains */ static void __init parse_cpu_affinity_structure(char *p) { - struct acpi_table_processor_affinity *cpu_affinity = - (struct acpi_table_processor_affinity *) p; + struct acpi_srat_cpu_affinity *cpu_affinity = + (struct acpi_srat_cpu_affinity *) p; - if (!cpu_affinity->flags.enabled) + if ((cpu_affinity->flags & ACPI_SRAT_CPU_ENABLED) == 0) return; /* empty entry */ /* mark this node as "seen" in node bitmap */ - BMAP_SET(pxm_bitmap, cpu_affinity->proximity_domain); + BMAP_SET(pxm_bitmap, cpu_affinity->proximity_domain_lo); - apicid_to_pxm[cpu_affinity->apic_id] = cpu_affinity->proximity_domain; + apicid_to_pxm[cpu_affinity->apic_id] = cpu_affinity->proximity_domain_lo; printk("CPU 0x%02X in proximity domain 0x%02X\n", - cpu_affinity->apic_id, cpu_affinity->proximity_domain); + cpu_affinity->apic_id, cpu_affinity->proximity_domain_lo); } /* @@ -84,28 +84,27 @@ static void __init parse_cpu_affinity_structure(char *p) static void __init parse_memory_affinity_structure (char *sratp) { unsigned long long paddr, size; - unsigned long start_pfn, end_pfn; + unsigned long start_pfn, end_pfn; u8 pxm; struct node_memory_chunk_s *p, *q, *pend; - struct acpi_table_memory_affinity *memory_affinity = - (struct acpi_table_memory_affinity *) sratp; + struct acpi_srat_mem_affinity *memory_affinity = + (struct acpi_srat_mem_affinity *) sratp; - if (!memory_affinity->flags.enabled) + if ((memory_affinity->flags & ACPI_SRAT_MEM_ENABLED) == 0) return; /* empty entry */ + pxm = memory_affinity->proximity_domain & 0xff; + /* mark this node as "seen" in node bitmap */ - BMAP_SET(pxm_bitmap, memory_affinity->proximity_domain); + BMAP_SET(pxm_bitmap, pxm); /* calculate info for memory chunk structure */ - paddr = memory_affinity->base_addr_hi; - paddr = (paddr << 32) | memory_affinity->base_addr_lo; - size = memory_affinity->length_hi; - size = (size << 32) | memory_affinity->length_lo; - + paddr = memory_affinity->base_address; + size = memory_affinity->length; + start_pfn = paddr >> PAGE_SHIFT; end_pfn = (paddr + size) >> PAGE_SHIFT; - - pxm = memory_affinity->proximity_domain; + if (num_memory_chunks >= MAXCHUNKS) { printk("Too many mem chunks in SRAT. Ignoring %lld MBytes at %llx\n", @@ -132,8 +131,8 @@ static void __init parse_memory_affinity_structure (char *sratp) printk("Memory range 0x%lX to 0x%lX (type 0x%X) in proximity domain 0x%02X %s\n", start_pfn, end_pfn, memory_affinity->memory_type, - memory_affinity->proximity_domain, - (memory_affinity->flags.hot_pluggable ? + pxm, + ((memory_affinity->flags & ACPI_SRAT_MEM_HOT_PLUGGABLE) ? "enabled and removable" : "enabled" ) ); } @@ -185,10 +184,10 @@ static int __init acpi20_parse_srat(struct acpi_table_srat *sratp) num_memory_chunks = 0; while (p < end) { switch (*p) { - case ACPI_SRAT_PROCESSOR_AFFINITY: + case ACPI_SRAT_TYPE_CPU_AFFINITY: parse_cpu_affinity_structure(p); break; - case ACPI_SRAT_MEMORY_AFFINITY: + case ACPI_SRAT_TYPE_MEMORY_AFFINITY: parse_memory_affinity_structure(p); break; default: @@ -262,31 +261,30 @@ out_fail: return 0; } +struct acpi_static_rsdt { + struct acpi_table_rsdt table; + u32 padding[7]; /* Allow for 7 more table entries */ +}; + int __init get_memcfg_from_srat(void) { struct acpi_table_header *header = NULL; struct acpi_table_rsdp *rsdp = NULL; struct acpi_table_rsdt *rsdt = NULL; - struct acpi_pointer *rsdp_address = NULL; - struct acpi_table_rsdt saved_rsdt; + acpi_native_uint rsdp_address = 0; + struct acpi_static_rsdt saved_rsdt; int tables = 0; int i = 0; - if (ACPI_FAILURE(acpi_find_root_pointer(ACPI_PHYSICAL_ADDRESSING, - rsdp_address))) { + rsdp_address = acpi_find_rsdp(); + if (!rsdp_address) { printk("%s: System description tables not found\n", __FUNCTION__); goto out_err; } - if (rsdp_address->pointer_type == ACPI_PHYSICAL_POINTER) { - printk("%s: assigning address to rsdp\n", __FUNCTION__); - rsdp = (struct acpi_table_rsdp *) - (u32)rsdp_address->pointer.physical; - } else { - printk("%s: rsdp_address is not a physical pointer\n", __FUNCTION__); - goto out_err; - } + printk("%s: assigning address to rsdp\n", __FUNCTION__); + rsdp = (struct acpi_table_rsdp *)(u32)rsdp_address; if (!rsdp) { printk("%s: Didn't find ACPI root!\n", __FUNCTION__); goto out_err; @@ -295,13 +293,13 @@ int __init get_memcfg_from_srat(void) printk(KERN_INFO "%.8s v%d [%.6s]\n", rsdp->signature, rsdp->revision, rsdp->oem_id); - if (strncmp(rsdp->signature, RSDP_SIG,strlen(RSDP_SIG))) { + if (strncmp(rsdp->signature, ACPI_SIG_RSDP,strlen(ACPI_SIG_RSDP))) { printk(KERN_WARNING "%s: RSDP table signature incorrect\n", __FUNCTION__); goto out_err; } rsdt = (struct acpi_table_rsdt *) - boot_ioremap(rsdp->rsdt_address, sizeof(struct acpi_table_rsdt)); + boot_ioremap(rsdp->rsdt_physical_address, sizeof(struct acpi_table_rsdt)); if (!rsdt) { printk(KERN_WARNING @@ -310,9 +308,9 @@ int __init get_memcfg_from_srat(void) goto out_err; } - header = & rsdt->header; + header = &rsdt->header; - if (strncmp(header->signature, RSDT_SIG, strlen(RSDT_SIG))) { + if (strncmp(header->signature, ACPI_SIG_RSDT, strlen(ACPI_SIG_RSDT))) { printk(KERN_WARNING "ACPI: RSDT signature incorrect\n"); goto out_err; } @@ -330,9 +328,9 @@ int __init get_memcfg_from_srat(void) memcpy(&saved_rsdt, rsdt, sizeof(saved_rsdt)); - if (saved_rsdt.header.length > sizeof(saved_rsdt)) { + if (saved_rsdt.table.header.length > sizeof(saved_rsdt)) { printk(KERN_WARNING "ACPI: Too big length in RSDT: %d\n", - saved_rsdt.header.length); + saved_rsdt.table.header.length); goto out_err; } @@ -341,15 +339,15 @@ int __init get_memcfg_from_srat(void) for (i = 0; i < tables; i++) { /* Map in header, then map in full table length. */ header = (struct acpi_table_header *) - boot_ioremap(saved_rsdt.entry[i], sizeof(struct acpi_table_header)); + boot_ioremap(saved_rsdt.table.table_offset_entry[i], sizeof(struct acpi_table_header)); if (!header) break; header = (struct acpi_table_header *) - boot_ioremap(saved_rsdt.entry[i], header->length); + boot_ioremap(saved_rsdt.table.table_offset_entry[i], header->length); if (!header) break; - if (strncmp((char *) &header->signature, "SRAT", 4)) + if (strncmp((char *) &header->signature, ACPI_SIG_SRAT, 4)) continue; /* we've found the srat table. don't need to look at any more tables */ -- cgit v0.10.2 From 45eded8703c0f9d58a8807f80baa9fe98ac0ec67 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 21:48:40 -0500 Subject: ACPI: fix HP RX2600 IA64 boot Copy space_id of GAS structure to newly created GAS. The previous FADT conversion code defaulted to IO space. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c index 273b5fd..a6723a2 100644 --- a/drivers/acpi/tables/tbfadt.c +++ b/drivers/acpi/tables/tbfadt.c @@ -333,6 +333,8 @@ static void acpi_tb_convert_fadt(void) pm1_register_length, (acpi_gbl_FADT.xpm1a_event_block.address + pm1_register_length)); + /* Don't forget to copy space_id of the GAS */ + acpi_gbl_xpm1a_enable.space_id = acpi_gbl_FADT.xpm1a_event_block.space_id; /* The PM1B register block is optional, ignore if not present */ @@ -341,6 +343,9 @@ static void acpi_tb_convert_fadt(void) pm1_register_length, (acpi_gbl_FADT.xpm1b_event_block. address + pm1_register_length)); + /* Don't forget to copy space_id of the GAS */ + acpi_gbl_xpm1b_enable.space_id = acpi_gbl_FADT.xpm1a_event_block.space_id; + } } -- cgit v0.10.2 From defad23020bb7701b3ad414135c73fc03054507b Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Fri, 2 Feb 2007 22:02:55 -0500 Subject: ACPI_NUMA: fix HP IA64 simulator issue with extended memory domain ACPI 3.0 incorporated the SRAT spec, upping the table version to 2, and extending the size of the proximity domain from 1-byte to 4-bytes. This extension was into a reserved field that firmware should set to 0, but the HP simulator had non-zero values there resulting in unexpected huge numbers. So mask the domain down to 8-bits for now. A more general fix will be to check the table version supplied by firmware and get paranoid about reserved fields. Signed-off-by: Alexey Starikovskiy Signed-off-by: Len Brown diff --git a/arch/ia64/kernel/acpi.c b/arch/ia64/kernel/acpi.c index 989ffc3..a99b0cc 100644 --- a/arch/ia64/kernel/acpi.c +++ b/arch/ia64/kernel/acpi.c @@ -422,8 +422,8 @@ static int get_memory_proximity_domain(struct acpi_srat_mem_affinity *ma) int pxm; pxm = ma->proximity_domain; - if (ia64_platform_is("sn2")) - pxm += ma->reserved << 8; + if (!ia64_platform_is("sn2")) + pxm &= 0xff; return pxm; } -- cgit v0.10.2 From 647fb47dfabeffd2f1706013ebf5cfc92b70d273 Mon Sep 17 00:00:00 2001 From: Len Brown Date: Fri, 2 Feb 2007 22:14:22 -0500 Subject: ACPICA: reduce conflicts with Altix patch series Syntax only -- no functional changes. Signed-off-by: Len Brown diff --git a/arch/ia64/sn/kernel/io_common.c b/arch/ia64/sn/kernel/io_common.c index 65979f1..75f0379 100644 --- a/arch/ia64/sn/kernel/io_common.c +++ b/arch/ia64/sn/kernel/io_common.c @@ -25,6 +25,7 @@ #include "xtalk/xwidgetdev.h" #include #include +#include extern void sn_init_cpei_timer(void); extern void register_sn_procfs(void); @@ -36,6 +37,7 @@ extern void sn_legacy_pci_window_fixup(struct pci_controller *, u64, u64); extern void sn_io_acpi_init(void); extern void sn_io_init(void); + static struct list_head sn_sysdata_list; /* sysdata list struct */ @@ -48,7 +50,7 @@ int sn_ioif_inited; /* SN I/O infrastructure initialized? */ struct sn_pcibus_provider *sn_pci_provider[PCIIO_ASIC_MAX_TYPES]; /* indexed by asic type */ -int sn_acpi_base_support() +int sn_acpi_base_support(void) { struct acpi_table_header *header; (void)acpi_get_table_by_index(ACPI_TABLE_INDEX_DSDT, &header); @@ -293,7 +295,7 @@ void sn_pci_fixup_slot(struct pci_dev *dev) list_add_tail(&pcidev_info->pdi_list, &(SN_PLATFORM_DATA(dev->bus)->pcidev_info)); - if (sn_acpi_base_support()) + if (SN_ACPI_BASE_SUPPORT()) sn_acpi_slot_fixup(dev, pcidev_info); else sn_more_slot_fixup(dev, pcidev_info); @@ -505,7 +507,7 @@ void __devinit sn_pci_fixup_bus(struct pci_bus *bus) { - if (sn_acpi_base_support()) + if (SN_ACPI_BASE_SUPPORT()) sn_acpi_bus_fixup(bus); else sn_bus_fixup(bus); @@ -551,9 +553,13 @@ sn_io_early_init(void) register_sn_procfs(); #endif - printk(KERN_INFO "ACPI DSDT OEM Rev 0x%x\n", - acpi_gbl_DSDT->oem_revision); - if (sn_acpi_base_support()) + { + struct acpi_table_header *header; + (void)acpi_get_table_by_index(ACPI_TABLE_INDEX_DSDT, &header); + printk(KERN_INFO "ACPI DSDT OEM Rev 0x%x\n", + header->oem_revision); + } + if (SN_ACPI_BASE_SUPPORT()) sn_io_acpi_init(); else sn_io_init(); diff --git a/arch/ia64/sn/kernel/iomv.c b/arch/ia64/sn/kernel/iomv.c index b1a47da..ab7e2fd 100644 --- a/arch/ia64/sn/kernel/iomv.c +++ b/arch/ia64/sn/kernel/iomv.c @@ -16,6 +16,7 @@ #include #include #include +#include #define IS_LEGACY_VGA_IOPORT(p) \ (((p) >= 0x3b0 && (p) <= 0x3bb) || ((p) >= 0x3c0 && (p) <= 0x3df)) @@ -29,8 +30,6 @@ * SN i/o address. Used by sn_in*() and sn_out*(). */ -extern int sn_acpi_base_support(); - void *sn_io_addr(unsigned long port) { if (!IS_RUNNING_ON_SIMULATOR()) { @@ -39,7 +38,7 @@ void *sn_io_addr(unsigned long port) /* On sn2, legacy I/O ports don't point at anything */ if (port < (64 * 1024)) return NULL; - if (sn_acpi_base_support()) + if (SN_ACPI_BASE_SUPPORT()) return (__ia64_mk_io_addr(port)); else return ((void *)(port | __IA64_UNCACHED_OFFSET)); diff --git a/include/asm-ia64/sn/acpi.h b/include/asm-ia64/sn/acpi.h new file mode 100644 index 0000000..7d6cb3b --- /dev/null +++ b/include/asm-ia64/sn/acpi.h @@ -0,0 +1,18 @@ +/* + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + * + * Copyright (C) 2006 Silicon Graphics, Inc. All rights reserved. + */ + +#ifndef _ASM_IA64_SN_ACPI_H +#define _ASM_IA64_SN_ACPI_H + +#include "acpi/acglobal.h" + +#define SN_ACPI_BASE_SUPPORT() sn_acpi_base_support() + +extern int sn_acpi_base_support(void); + +#endif /* _ASM_IA64_SN_ACPI_H */ -- cgit v0.10.2 From 6f09a9250a5d76c0765cd51a33e0a042e9761cfc Mon Sep 17 00:00:00 2001 From: John Keller Date: Tue, 30 Jan 2007 01:17:37 -0500 Subject: Altix: ACPI SSDT PCI device support Add SN platform support for running with an ACPI capable PROM that defines PCI devices in SSDT tables. There is a SSDT table for every occupied slot on a root bus, containing info for every PPB and/or device on the bus. The SSDTs will be dynamically loaded/unloaded at hotplug enable/disable. Platform specific information that is currently passed via a SAL call, will now be passed via the Vendor resource in the ACPI Device object(s) defined in each SSDT. Signed-off-by: John Keller Cc: Greg KH Cc: "Luck, Tony" Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/arch/ia64/sn/kernel/io_acpi_init.c b/arch/ia64/sn/kernel/io_acpi_init.c index cb96b4e..8c331ca 100644 --- a/arch/ia64/sn/kernel/io_acpi_init.c +++ b/arch/ia64/sn/kernel/io_acpi_init.c @@ -13,6 +13,7 @@ #include #include "xtalk/hubdev.h" #include +#include /* @@ -31,6 +32,12 @@ struct acpi_vendor_uuid sn_uuid = { 0xa2, 0x7c, 0x08, 0x00, 0x69, 0x13, 0xea, 0x51 }, }; +struct sn_pcidev_match { + u8 bus; + unsigned int devfn; + acpi_handle handle; +}; + /* * Perform the early IO init in PROM. */ @@ -119,9 +126,11 @@ sn_get_bussoft_ptr(struct pci_bus *bus) status = acpi_get_vendor_resource(handle, METHOD_NAME__CRS, &sn_uuid, &buffer); if (ACPI_FAILURE(status)) { - printk(KERN_ERR "get_acpi_pcibus_ptr: " - "get_acpi_bussoft_info() failed: %d\n", - status); + printk(KERN_ERR "%s: " + "acpi_get_vendor_resource() failed (0x%x) for: ", + __FUNCTION__, status); + acpi_ns_print_node_pathname(handle, NULL); + printk("\n"); return NULL; } resource = buffer.pointer; @@ -130,8 +139,8 @@ sn_get_bussoft_ptr(struct pci_bus *bus) if ((vendor->byte_length - sizeof(struct acpi_vendor_uuid)) != sizeof(struct pcibus_bussoft *)) { printk(KERN_ERR - "get_acpi_bussoft_ptr: Invalid vendor data " - "length %d\n", vendor->byte_length); + "%s: Invalid vendor data length %d\n", + __FUNCTION__, vendor->byte_length); kfree(buffer.pointer); return NULL; } @@ -143,34 +152,254 @@ sn_get_bussoft_ptr(struct pci_bus *bus) } /* - * sn_acpi_bus_fixup + * sn_extract_device_info - Extract the pcidev_info and the sn_irq_info + * pointers from the vendor resource using the + * provided acpi handle, and copy the structures + * into the argument buffers. */ -void -sn_acpi_bus_fixup(struct pci_bus *bus) +static int +sn_extract_device_info(acpi_handle handle, struct pcidev_info **pcidev_info, + struct sn_irq_info **sn_irq_info) { - struct pci_dev *pci_dev = NULL; - struct pcibus_bussoft *prom_bussoft_ptr; - extern void sn_common_bus_fixup(struct pci_bus *, - struct pcibus_bussoft *); + u64 addr; + struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; + struct sn_irq_info *irq_info, *irq_info_prom; + struct pcidev_info *pcidev_ptr, *pcidev_prom_ptr; + struct acpi_resource *resource; + int ret = 0; + acpi_status status; + struct acpi_resource_vendor_typed *vendor; - if (!bus->parent) { /* If root bus */ - prom_bussoft_ptr = sn_get_bussoft_ptr(bus); - if (prom_bussoft_ptr == NULL) { + /* + * The pointer to this device's pcidev_info structure in + * the PROM, is in the vendor resource. + */ + status = acpi_get_vendor_resource(handle, METHOD_NAME__CRS, + &sn_uuid, &buffer); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR + "%s: acpi_get_vendor_resource() failed (0x%x) for: ", + __FUNCTION__, status); + acpi_ns_print_node_pathname(handle, NULL); + printk("\n"); + return 1; + } + + resource = buffer.pointer; + vendor = &resource->data.vendor_typed; + if ((vendor->byte_length - sizeof(struct acpi_vendor_uuid)) != + sizeof(struct pci_devdev_info *)) { + printk(KERN_ERR + "%s: Invalid vendor data length: %d for: ", + __FUNCTION__, vendor->byte_length); + acpi_ns_print_node_pathname(handle, NULL); + printk("\n"); + ret = 1; + goto exit; + } + + pcidev_ptr = kzalloc(sizeof(struct pcidev_info), GFP_KERNEL); + if (!pcidev_ptr) + panic("%s: Unable to alloc memory for pcidev_info", __FUNCTION__); + + memcpy(&addr, vendor->byte_data, sizeof(struct pcidev_info *)); + pcidev_prom_ptr = __va(addr); + memcpy(pcidev_ptr, pcidev_prom_ptr, sizeof(struct pcidev_info)); + + /* Get the IRQ info */ + irq_info = kzalloc(sizeof(struct sn_irq_info), GFP_KERNEL); + if (!irq_info) + panic("%s: Unable to alloc memory for sn_irq_info", __FUNCTION__); + + if (pcidev_ptr->pdi_sn_irq_info) { + irq_info_prom = __va(pcidev_ptr->pdi_sn_irq_info); + memcpy(irq_info, irq_info_prom, sizeof(struct sn_irq_info)); + } + + *pcidev_info = pcidev_ptr; + *sn_irq_info = irq_info; + +exit: + kfree(buffer.pointer); + return ret; +} + +static unsigned int +get_host_devfn(acpi_handle device_handle, acpi_handle rootbus_handle) +{ + unsigned long adr; + acpi_handle child; + unsigned int devfn; + int function; + acpi_handle parent; + int slot; + acpi_status status; + + /* + * Do an upward search to find the root bus device, and + * obtain the host devfn from the previous child device. + */ + child = device_handle; + while (child) { + status = acpi_get_parent(child, &parent); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR "%s: acpi_get_parent() failed " + "(0x%x) for: ", __FUNCTION__, status); + acpi_ns_print_node_pathname(child, NULL); + printk("\n"); + panic("%s: Unable to find host devfn\n", __FUNCTION__); + } + if (parent == rootbus_handle) + break; + child = parent; + } + if (!child) { + printk(KERN_ERR "%s: Unable to find root bus for: ", + __FUNCTION__); + acpi_ns_print_node_pathname(device_handle, NULL); + printk("\n"); + BUG(); + } + + status = acpi_evaluate_integer(child, METHOD_NAME__ADR, NULL, &adr); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR "%s: Unable to get _ADR (0x%x) for: ", + __FUNCTION__, status); + acpi_ns_print_node_pathname(child, NULL); + printk("\n"); + panic("%s: Unable to find host devfn\n", __FUNCTION__); + } + + slot = (adr >> 16) & 0xffff; + function = adr & 0xffff; + devfn = PCI_DEVFN(slot, function); + return devfn; +} + +/* + * find_matching_device - Callback routine to find the ACPI device + * that matches up with our pci_dev device. + * Matching is done on bus number and devfn. + * To find the bus number for a particular + * ACPI device, we must look at the _BBN method + * of its parent. + */ +static acpi_status +find_matching_device(acpi_handle handle, u32 lvl, void *context, void **rv) +{ + unsigned long bbn = -1; + unsigned long adr; + acpi_handle parent = NULL; + acpi_status status; + unsigned int devfn; + int function; + int slot; + struct sn_pcidev_match *info = context; + + status = acpi_evaluate_integer(handle, METHOD_NAME__ADR, NULL, + &adr); + if (ACPI_SUCCESS(status)) { + status = acpi_get_parent(handle, &parent); + if (ACPI_FAILURE(status)) { printk(KERN_ERR - "sn_pci_fixup_bus: 0x%04x:0x%02x Unable to " - "obtain prom_bussoft_ptr\n", - pci_domain_nr(bus), bus->number); - return; + "%s: acpi_get_parent() failed (0x%x) for: ", + __FUNCTION__, status); + acpi_ns_print_node_pathname(handle, NULL); + printk("\n"); + return AE_OK; + } + status = acpi_evaluate_integer(parent, METHOD_NAME__BBN, + NULL, &bbn); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR + "%s: Failed to find _BBN in parent of: ", + __FUNCTION__); + acpi_ns_print_node_pathname(handle, NULL); + printk("\n"); + return AE_OK; + } + + slot = (adr >> 16) & 0xffff; + function = adr & 0xffff; + devfn = PCI_DEVFN(slot, function); + if ((info->devfn == devfn) && (info->bus == bbn)) { + /* We have a match! */ + info->handle = handle; + return 1; } - sn_common_bus_fixup(bus, prom_bussoft_ptr); } - list_for_each_entry(pci_dev, &bus->devices, bus_list) { - sn_pci_fixup_slot(pci_dev); + return AE_OK; +} + +/* + * sn_acpi_get_pcidev_info - Search ACPI namespace for the acpi + * device matching the specified pci_dev, + * and return the pcidev info and irq info. + */ +int +sn_acpi_get_pcidev_info(struct pci_dev *dev, struct pcidev_info **pcidev_info, + struct sn_irq_info **sn_irq_info) +{ + unsigned int host_devfn; + struct sn_pcidev_match pcidev_match; + acpi_handle rootbus_handle; + unsigned long segment; + acpi_status status; + + rootbus_handle = PCI_CONTROLLER(dev)->acpi_handle; + status = acpi_evaluate_integer(rootbus_handle, METHOD_NAME__SEG, NULL, + &segment); + if (ACPI_SUCCESS(status)) { + if (segment != pci_domain_nr(dev)) { + printk(KERN_ERR + "%s: Segment number mismatch, 0x%lx vs 0x%x for: ", + __FUNCTION__, segment, pci_domain_nr(dev)); + acpi_ns_print_node_pathname(rootbus_handle, NULL); + printk("\n"); + return 1; + } + } else { + printk(KERN_ERR "%s: Unable to get __SEG from: ", + __FUNCTION__); + acpi_ns_print_node_pathname(rootbus_handle, NULL); + printk("\n"); + return 1; + } + + /* + * We want to search all devices in this segment/domain + * of the ACPI namespace for the matching ACPI device, + * which holds the pcidev_info pointer in its vendor resource. + */ + pcidev_match.bus = dev->bus->number; + pcidev_match.devfn = dev->devfn; + pcidev_match.handle = NULL; + + acpi_walk_namespace(ACPI_TYPE_DEVICE, rootbus_handle, ACPI_UINT32_MAX, + find_matching_device, &pcidev_match, NULL); + + if (!pcidev_match.handle) { + printk(KERN_ERR + "%s: Could not find matching ACPI device for %s.\n", + __FUNCTION__, pci_name(dev)); + return 1; } + + if (sn_extract_device_info(pcidev_match.handle, pcidev_info, sn_irq_info)) + return 1; + + /* Build up the pcidev_info.pdi_slot_host_handle */ + host_devfn = get_host_devfn(pcidev_match.handle, rootbus_handle); + (*pcidev_info)->pdi_slot_host_handle = + ((unsigned long) pci_domain_nr(dev) << 40) | + /* bus == 0 */ + host_devfn; + return 0; } /* - * sn_acpi_slot_fixup - Perform any SN specific slot fixup. + * sn_acpi_slot_fixup - Obtain the pcidev_info and sn_irq_info. + * Perform any SN specific slot fixup. * At present there does not appear to be * any generic way to handle a ROM image * that has been shadowed by the PROM, so @@ -179,11 +408,18 @@ sn_acpi_bus_fixup(struct pci_bus *bus) */ void -sn_acpi_slot_fixup(struct pci_dev *dev, struct pcidev_info *pcidev_info) +sn_acpi_slot_fixup(struct pci_dev *dev) { void __iomem *addr; + struct pcidev_info *pcidev_info = NULL; + struct sn_irq_info *sn_irq_info = NULL; size_t size; + if (sn_acpi_get_pcidev_info(dev, &pcidev_info, &sn_irq_info)) { + panic("%s: Failure obtaining pcidev_info for %s\n", + __FUNCTION__, pci_name(dev)); + } + if (pcidev_info->pdi_pio_mapped_addr[PCI_ROM_RESOURCE]) { /* * A valid ROM image exists and has been shadowed by the @@ -200,8 +436,11 @@ sn_acpi_slot_fixup(struct pci_dev *dev, struct pcidev_info *pcidev_info) (unsigned long) addr + size; dev->resource[PCI_ROM_RESOURCE].flags |= IORESOURCE_ROM_BIOS_COPY; } + sn_pci_fixup_slot(dev, pcidev_info, sn_irq_info); } +EXPORT_SYMBOL(sn_acpi_slot_fixup); + static struct acpi_driver acpi_sn_hubdev_driver = { .name = "SGI HUBDEV Driver", .ids = "SGIHUB,SGITIO", @@ -212,6 +451,33 @@ static struct acpi_driver acpi_sn_hubdev_driver = { /* + * sn_acpi_bus_fixup - Perform SN specific setup of software structs + * (pcibus_bussoft, pcidev_info) and hardware + * registers, for the specified bus and devices under it. + */ +void +sn_acpi_bus_fixup(struct pci_bus *bus) +{ + struct pci_dev *pci_dev = NULL; + struct pcibus_bussoft *prom_bussoft_ptr; + + if (!bus->parent) { /* If root bus */ + prom_bussoft_ptr = sn_get_bussoft_ptr(bus); + if (prom_bussoft_ptr == NULL) { + printk(KERN_ERR + "%s: 0x%04x:0x%02x Unable to " + "obtain prom_bussoft_ptr\n", + __FUNCTION__, pci_domain_nr(bus), bus->number); + return; + } + sn_common_bus_fixup(bus, prom_bussoft_ptr); + } + list_for_each_entry(pci_dev, &bus->devices, bus_list) { + sn_acpi_slot_fixup(pci_dev); + } +} + +/* * sn_io_acpi_init - PROM has ACPI support for IO, defining at a minimum the * nodes and root buses in the DSDT. As a result, bus scanning * will be initiated by the Linux ACPI code. diff --git a/arch/ia64/sn/kernel/io_common.c b/arch/ia64/sn/kernel/io_common.c index 75f0379..d48bcd8 100644 --- a/arch/ia64/sn/kernel/io_common.c +++ b/arch/ia64/sn/kernel/io_common.c @@ -26,14 +26,10 @@ #include #include #include +#include "acpi/acglobal.h" extern void sn_init_cpei_timer(void); extern void register_sn_procfs(void); -extern void sn_acpi_bus_fixup(struct pci_bus *); -extern void sn_bus_fixup(struct pci_bus *); -extern void sn_acpi_slot_fixup(struct pci_dev *, struct pcidev_info *); -extern void sn_more_slot_fixup(struct pci_dev *, struct pcidev_info *); -extern void sn_legacy_pci_window_fixup(struct pci_controller *, u64, u64); extern void sn_io_acpi_init(void); extern void sn_io_init(void); @@ -48,16 +44,10 @@ struct sysdata_el { int sn_ioif_inited; /* SN I/O infrastructure initialized? */ -struct sn_pcibus_provider *sn_pci_provider[PCIIO_ASIC_MAX_TYPES]; /* indexed by asic type */ +int sn_acpi_rev; /* SN ACPI revision */ +EXPORT_SYMBOL_GPL(sn_acpi_rev); -int sn_acpi_base_support(void) -{ - struct acpi_table_header *header; - (void)acpi_get_table_by_index(ACPI_TABLE_INDEX_DSDT, &header); - if (header && header->oem_revision >= 0x20101) - return 1; - return 0; -} +struct sn_pcibus_provider *sn_pci_provider[PCIIO_ASIC_MAX_TYPES]; /* indexed by asic type */ /* * Hooks and struct for unsupported pci providers @@ -108,25 +98,6 @@ sal_get_device_dmaflush_list(u64 nasid, u64 widget_num, u64 device_num, } /* - * Retrieve the pci device information given the bus and device|function number. - */ -static inline u64 -sal_get_pcidev_info(u64 segment, u64 bus_number, u64 devfn, u64 pci_dev, - u64 sn_irq_info) -{ - struct ia64_sal_retval ret_stuff; - ret_stuff.status = 0; - ret_stuff.v0 = 0; - - SAL_CALL_NOLOCK(ret_stuff, - (u64) SN_SAL_IOIF_GET_PCIDEV_INFO, - (u64) segment, (u64) bus_number, (u64) devfn, - (u64) pci_dev, - sn_irq_info, 0, 0); - return ret_stuff.v0; -} - -/* * sn_pcidev_info_get() - Retrieve the pcidev_info struct for the specified * device. */ @@ -258,50 +229,25 @@ void sn_pci_unfixup_slot(struct pci_dev *dev) } /* - * sn_pci_fixup_slot() - This routine sets up a slot's resources consistent - * with the Linux PCI abstraction layer. Resources - * acquired from our PCI provider include PIO maps - * to BAR space and interrupt objects. + * sn_pci_fixup_slot() */ -void sn_pci_fixup_slot(struct pci_dev *dev) +void sn_pci_fixup_slot(struct pci_dev *dev, struct pcidev_info *pcidev_info, + struct sn_irq_info *sn_irq_info) { int segment = pci_domain_nr(dev->bus); - int status = 0; struct pcibus_bussoft *bs; - struct pci_bus *host_pci_bus; - struct pci_dev *host_pci_dev; - struct pcidev_info *pcidev_info; - struct sn_irq_info *sn_irq_info; - unsigned int bus_no, devfn; + struct pci_bus *host_pci_bus; + struct pci_dev *host_pci_dev; + unsigned int bus_no, devfn; pci_dev_get(dev); /* for the sysdata pointer */ - pcidev_info = kzalloc(sizeof(struct pcidev_info), GFP_KERNEL); - if (!pcidev_info) - BUG(); /* Cannot afford to run out of memory */ - - sn_irq_info = kzalloc(sizeof(struct sn_irq_info), GFP_KERNEL); - if (!sn_irq_info) - BUG(); /* Cannot afford to run out of memory */ - - /* Call to retrieve pci device information needed by kernel. */ - status = sal_get_pcidev_info((u64) segment, (u64) dev->bus->number, - dev->devfn, - (u64) __pa(pcidev_info), - (u64) __pa(sn_irq_info)); - if (status) - BUG(); /* Cannot get platform pci device information */ /* Add pcidev_info to list in pci_controller.platform_data */ list_add_tail(&pcidev_info->pdi_list, &(SN_PLATFORM_DATA(dev->bus)->pcidev_info)); - - if (SN_ACPI_BASE_SUPPORT()) - sn_acpi_slot_fixup(dev, pcidev_info); - else - sn_more_slot_fixup(dev, pcidev_info); /* * Using the PROMs values for the PCI host bus, get the Linux - * PCI host_pci_dev struct and set up host bus linkages + * PCI host_pci_dev struct and set up host bus linkages */ bus_no = (pcidev_info->pdi_slot_host_handle >> 32) & 0xff; @@ -498,11 +444,6 @@ void sn_generate_path(struct pci_bus *pci_bus, char *address) sprintf(address, "%s^%d", address, geo_slot(geoid)); } -/* - * sn_pci_fixup_bus() - Perform SN specific setup of software structs - * (pcibus_bussoft, pcidev_info) and hardware - * registers, for the specified bus and devices under it. - */ void __devinit sn_pci_fixup_bus(struct pci_bus *bus) { @@ -528,6 +469,15 @@ sn_io_early_init(void) if (!ia64_platform_is("sn2") || IS_RUNNING_ON_FAKE_PROM()) return 0; + /* we set the acpi revision to that of the DSDT table OEM rev. */ + { + struct acpi_table_header *header = NULL; + + acpi_get_table_by_index(ACPI_TABLE_INDEX_DSDT, &header); + BUG_ON(header == NULL); + sn_acpi_rev = header->oem_revision; + } + /* * prime sn_pci_provider[]. Individial provider init routines will * override their respective default entries. @@ -618,7 +568,6 @@ sn_io_late_init(void) fs_initcall(sn_io_late_init); -EXPORT_SYMBOL(sn_pci_fixup_slot); EXPORT_SYMBOL(sn_pci_unfixup_slot); EXPORT_SYMBOL(sn_bus_store_sysdata); EXPORT_SYMBOL(sn_bus_free_sysdata); diff --git a/arch/ia64/sn/kernel/io_init.c b/arch/ia64/sn/kernel/io_init.c index 9ad843e..600be3e 100644 --- a/arch/ia64/sn/kernel/io_init.c +++ b/arch/ia64/sn/kernel/io_init.c @@ -56,6 +56,25 @@ static inline u64 sal_get_pcibus_info(u64 segment, u64 busnum, u64 address) return ret_stuff.v0; } +/* + * Retrieve the pci device information given the bus and device|function number. + */ +static inline u64 +sal_get_pcidev_info(u64 segment, u64 bus_number, u64 devfn, u64 pci_dev, + u64 sn_irq_info) +{ + struct ia64_sal_retval ret_stuff; + ret_stuff.status = 0; + ret_stuff.v0 = 0; + + SAL_CALL_NOLOCK(ret_stuff, + (u64) SN_SAL_IOIF_GET_PCIDEV_INFO, + (u64) segment, (u64) bus_number, (u64) devfn, + (u64) pci_dev, + sn_irq_info, 0, 0); + return ret_stuff.v0; +} + /* * sn_fixup_ionodes() - This routine initializes the HUB data structure for @@ -172,18 +191,40 @@ sn_pci_window_fixup(struct pci_dev *dev, unsigned int count, } /* - * sn_more_slot_fixup() - We are not running with an ACPI capable PROM, + * sn_io_slot_fixup() - We are not running with an ACPI capable PROM, * and need to convert the pci_dev->resource * 'start' and 'end' addresses to mapped addresses, * and setup the pci_controller->window array entries. */ void -sn_more_slot_fixup(struct pci_dev *dev, struct pcidev_info *pcidev_info) +sn_io_slot_fixup(struct pci_dev *dev) { unsigned int count = 0; int idx; s64 pci_addrs[PCI_ROM_RESOURCE + 1]; unsigned long addr, end, size, start; + struct pcidev_info *pcidev_info; + struct sn_irq_info *sn_irq_info; + int status; + + pcidev_info = kzalloc(sizeof(struct pcidev_info), GFP_KERNEL); + if (!pcidev_info) + panic("%s: Unable to alloc memory for pcidev_info", __FUNCTION__); + + sn_irq_info = kzalloc(sizeof(struct sn_irq_info), GFP_KERNEL); + if (!sn_irq_info) + panic("%s: Unable to alloc memory for sn_irq_info", __FUNCTION__); + + /* Call to retrieve pci device information needed by kernel. */ + status = sal_get_pcidev_info((u64) pci_domain_nr(dev), + (u64) dev->bus->number, + dev->devfn, + (u64) __pa(pcidev_info), + (u64) __pa(sn_irq_info)); + + if (status) + BUG(); /* Cannot get platform pci device information */ + /* Copy over PIO Mapped Addresses */ for (idx = 0; idx <= PCI_ROM_RESOURCE; idx++) { @@ -219,8 +260,12 @@ sn_more_slot_fixup(struct pci_dev *dev, struct pcidev_info *pcidev_info) */ if (count > 0) sn_pci_window_fixup(dev, count, pci_addrs); + + sn_pci_fixup_slot(dev, pcidev_info, sn_irq_info); } +EXPORT_SYMBOL(sn_io_slot_fixup); + /* * sn_pci_controller_fixup() - This routine sets up a bus's resources * consistent with the Linux PCI abstraction layer. @@ -272,9 +317,6 @@ sn_bus_fixup(struct pci_bus *bus) { struct pci_dev *pci_dev = NULL; struct pcibus_bussoft *prom_bussoft_ptr; - extern void sn_common_bus_fixup(struct pci_bus *, - struct pcibus_bussoft *); - if (!bus->parent) { /* If root bus */ prom_bussoft_ptr = PCI_CONTROLLER(bus)->platform_data; @@ -291,7 +333,7 @@ sn_bus_fixup(struct pci_bus *bus) prom_bussoft_ptr->bs_legacy_mem); } list_for_each_entry(pci_dev, &bus->devices, bus_list) { - sn_pci_fixup_slot(pci_dev); + sn_io_slot_fixup(pci_dev); } } diff --git a/arch/ia64/sn/pci/pcibr/pcibr_provider.c b/arch/ia64/sn/pci/pcibr/pcibr_provider.c index 6846dc9..04a82560 100644 --- a/arch/ia64/sn/pci/pcibr/pcibr_provider.c +++ b/arch/ia64/sn/pci/pcibr/pcibr_provider.c @@ -20,7 +20,8 @@ #include "xtalk/hubdev.h" int -sal_pcibr_slot_enable(struct pcibus_info *soft, int device, void *resp) +sal_pcibr_slot_enable(struct pcibus_info *soft, int device, void *resp, + char **ssdt) { struct ia64_sal_retval ret_stuff; u64 busnum; @@ -32,7 +33,8 @@ sal_pcibr_slot_enable(struct pcibus_info *soft, int device, void *resp) segment = soft->pbi_buscommon.bs_persist_segment; busnum = soft->pbi_buscommon.bs_persist_busnum; SAL_CALL_NOLOCK(ret_stuff, (u64) SN_SAL_IOIF_SLOT_ENABLE, segment, - busnum, (u64) device, (u64) resp, 0, 0, 0); + busnum, (u64) device, (u64) resp, (u64)ia64_tpa(ssdt), + 0, 0); return (int)ret_stuff.v0; } diff --git a/include/asm-ia64/sn/acpi.h b/include/asm-ia64/sn/acpi.h index 7d6cb3b..9ce2801 100644 --- a/include/asm-ia64/sn/acpi.h +++ b/include/asm-ia64/sn/acpi.h @@ -11,8 +11,7 @@ #include "acpi/acglobal.h" -#define SN_ACPI_BASE_SUPPORT() sn_acpi_base_support() - -extern int sn_acpi_base_support(void); +extern int sn_acpi_rev; +#define SN_ACPI_BASE_SUPPORT() (sn_acpi_rev >= 0x20101) #endif /* _ASM_IA64_SN_ACPI_H */ diff --git a/include/asm-ia64/sn/pcibr_provider.h b/include/asm-ia64/sn/pcibr_provider.h index da3eade..17cb6cc 100644 --- a/include/asm-ia64/sn/pcibr_provider.h +++ b/include/asm-ia64/sn/pcibr_provider.h @@ -142,7 +142,7 @@ extern int pcibr_ate_alloc(struct pcibus_info *, int); extern void pcibr_ate_free(struct pcibus_info *, int); extern void ate_write(struct pcibus_info *, int, int, u64); extern int sal_pcibr_slot_enable(struct pcibus_info *soft, int device, - void *resp); + void *resp, char **ssdt); extern int sal_pcibr_slot_disable(struct pcibus_info *soft, int device, int action, void *resp); extern u16 sn_ioboard_to_pci_bus(struct pci_bus *pci_bus); diff --git a/include/asm-ia64/sn/pcidev.h b/include/asm-ia64/sn/pcidev.h index 9fe89a9..1c2382c 100644 --- a/include/asm-ia64/sn/pcidev.h +++ b/include/asm-ia64/sn/pcidev.h @@ -70,10 +70,16 @@ extern void sn_irq_fixup(struct pci_dev *pci_dev, struct sn_irq_info *sn_irq_info); extern void sn_irq_unfixup(struct pci_dev *pci_dev); extern struct pcidev_info * sn_pcidev_info_get(struct pci_dev *); +extern void sn_bus_fixup(struct pci_bus *); +extern void sn_acpi_bus_fixup(struct pci_bus *); +extern void sn_common_bus_fixup(struct pci_bus *, struct pcibus_bussoft *); extern void sn_bus_store_sysdata(struct pci_dev *dev); extern void sn_bus_free_sysdata(void); extern void sn_generate_path(struct pci_bus *pci_bus, char *address); -extern void sn_pci_fixup_slot(struct pci_dev *dev); +extern void sn_io_slot_fixup(struct pci_dev *); +extern void sn_acpi_slot_fixup(struct pci_dev *); +extern void sn_pci_fixup_slot(struct pci_dev *dev, struct pcidev_info *, + struct sn_irq_info *); extern void sn_pci_unfixup_slot(struct pci_dev *dev); extern void sn_irq_lh_init(void); #endif /* _ASM_IA64_SN_PCI_PCIDEV_H */ -- cgit v0.10.2 From 3e643e77a929202455a0cc868c2030a5ba8d1371 Mon Sep 17 00:00:00 2001 From: John Keller Date: Tue, 30 Jan 2007 01:18:38 -0500 Subject: Altix: Add ACPI SSDT PCI device support (hotplug) Support for dynamic loading and unloading of ACPI SSDT tables upon slot hotplugs and unplugs. On SN platforms, we now represent every populated root bus slot with a single ACPI SSDT table containing info for every device and PPB attached to the slot. These SSDTs are generated by the prom at initial boot and hotplug time. The info in these SSDT tables is used by the SN kernel IO "fixup" code (which is called at boot and hotplug time). On hotplugs (i.e. enable_slot()), if running with an ACPI capable prom, attempt to obtain a new ACPI SSDT table for the slot being hotplugged. If successful, add the table to the ACPI namespace (acpi_load_table()) and then walk the new devices and add them to the ACPI infrastructure (acpi_bus_add()). On hot unplugs (i.e. disable_slot()), if running with an ACPI capable prom, attempt to remove the SSDT table associated with the slot from the ACPI namespace (acpi_unload_table_id()) and infastructure (acpi_bus_trim()). From: John Keller A bug was fixed where the sgi hotplug driver was removing the slot's SSDT table from the ACPI namespace a bit too early in disable_slot(). Also, we now call acpi_bus_start() subsequent to acpi_bus_add(). Signed-off-by: Aaron Young Cc: Greg KH Cc: "Luck, Tony" Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/drivers/pci/hotplug/sgi_hotplug.c b/drivers/pci/hotplug/sgi_hotplug.c index 5d188c5..78cf071 100644 --- a/drivers/pci/hotplug/sgi_hotplug.c +++ b/drivers/pci/hotplug/sgi_hotplug.c @@ -28,6 +28,8 @@ #include #include #include +#include +#include #include "../pci.h" @@ -35,14 +37,17 @@ MODULE_LICENSE("GPL"); MODULE_AUTHOR("SGI (prarit@sgi.com, dickie@sgi.com, habeck@sgi.com)"); MODULE_DESCRIPTION("SGI Altix Hot Plug PCI Controller Driver"); -#define PCIIO_ASIC_TYPE_TIOCA 4 + +/* SAL call error codes. Keep in sync with prom header io/include/pcibr.h */ #define PCI_SLOT_ALREADY_UP 2 /* slot already up */ #define PCI_SLOT_ALREADY_DOWN 3 /* slot already down */ #define PCI_L1_ERR 7 /* L1 console command error */ #define PCI_EMPTY_33MHZ 15 /* empty 33 MHz bus */ + + +#define PCIIO_ASIC_TYPE_TIOCA 4 #define PCI_L1_QSIZE 128 /* our L1 message buffer size */ #define SN_MAX_HP_SLOTS 32 /* max hotplug slots */ -#define SGI_HOTPLUG_PROM_REV 0x0430 /* Min. required PROM version */ #define SN_SLOT_NAME_SIZE 33 /* size of name string */ /* internal list head */ @@ -227,7 +232,7 @@ static void sn_bus_free_data(struct pci_dev *dev) } static int sn_slot_enable(struct hotplug_slot *bss_hotplug_slot, - int device_num) + int device_num, char **ssdt) { struct slot *slot = bss_hotplug_slot->private; struct pcibus_info *pcibus_info; @@ -240,7 +245,8 @@ static int sn_slot_enable(struct hotplug_slot *bss_hotplug_slot, * Power-on and initialize the slot in the SN * PCI infrastructure. */ - rc = sal_pcibr_slot_enable(pcibus_info, device_num, &resp); + rc = sal_pcibr_slot_enable(pcibus_info, device_num, &resp, ssdt); + if (rc == PCI_SLOT_ALREADY_UP) { dev_dbg(slot->pci_bus->self, "is already active\n"); @@ -335,6 +341,7 @@ static int enable_slot(struct hotplug_slot *bss_hotplug_slot) int func, num_funcs; int new_ppb = 0; int rc; + char *ssdt = NULL; void pcibios_fixup_device_resources(struct pci_dev *); /* Serialize the Linux PCI infrastructure */ @@ -342,14 +349,29 @@ static int enable_slot(struct hotplug_slot *bss_hotplug_slot) /* * Power-on and initialize the slot in the SN - * PCI infrastructure. + * PCI infrastructure. Also, retrieve the ACPI SSDT + * table for the slot (if ACPI capable PROM). */ - rc = sn_slot_enable(bss_hotplug_slot, slot->device_num); + rc = sn_slot_enable(bss_hotplug_slot, slot->device_num, &ssdt); if (rc) { mutex_unlock(&sn_hotplug_mutex); return rc; } + if (ssdt) + ssdt = __va(ssdt); + /* Add the new SSDT for the slot to the ACPI namespace */ + if (SN_ACPI_BASE_SUPPORT() && ssdt) { + acpi_status ret; + + ret = acpi_load_table((struct acpi_table_header *)ssdt); + if (ACPI_FAILURE(ret)) { + printk(KERN_ERR "%s: acpi_load_table failed (0x%x)\n", + __FUNCTION__, ret); + /* try to continue on */ + } + } + num_funcs = pci_scan_slot(slot->pci_bus, PCI_DEVFN(slot->device_num + 1, 0)); if (!num_funcs) { @@ -374,7 +396,10 @@ static int enable_slot(struct hotplug_slot *bss_hotplug_slot) * pdi_host_pcidev_info). */ pcibios_fixup_device_resources(dev); - sn_pci_fixup_slot(dev); + if (SN_ACPI_BASE_SUPPORT()) + sn_acpi_slot_fixup(dev); + else + sn_io_slot_fixup(dev); if (dev->hdr_type == PCI_HEADER_TYPE_BRIDGE) { unsigned char sec_bus; pci_read_config_byte(dev, PCI_SECONDARY_BUS, @@ -388,6 +413,63 @@ static int enable_slot(struct hotplug_slot *bss_hotplug_slot) } } + /* + * Add the slot's devices to the ACPI infrastructure */ + if (SN_ACPI_BASE_SUPPORT() && ssdt) { + unsigned long adr; + struct acpi_device *pdevice; + struct acpi_device *device; + acpi_handle phandle; + acpi_handle chandle = NULL; + acpi_handle rethandle; + acpi_status ret; + + phandle = PCI_CONTROLLER(slot->pci_bus)->acpi_handle; + + if (acpi_bus_get_device(phandle, &pdevice)) { + dev_dbg(slot->pci_bus->self, + "no parent device, assuming NULL\n"); + pdevice = NULL; + } + + /* + * Walk the rootbus node's immediate children looking for + * the slot's device node(s). There can be more than + * one for multifunction devices. + */ + for (;;) { + rethandle = NULL; + ret = acpi_get_next_object(ACPI_TYPE_DEVICE, + phandle, chandle, + &rethandle); + + if (ret == AE_NOT_FOUND || rethandle == NULL) + break; + + chandle = rethandle; + + ret = acpi_evaluate_integer(chandle, METHOD_NAME__ADR, + NULL, &adr); + + if (ACPI_SUCCESS(ret) && + (adr>>16) == (slot->device_num + 1)) { + + ret = acpi_bus_add(&device, pdevice, chandle, + ACPI_BUS_TYPE_DEVICE); + if (ACPI_FAILURE(ret)) { + printk(KERN_ERR "%s: acpi_bus_add " + "failed (0x%x) for slot %d " + "func %d\n", __FUNCTION__, + ret, (int)(adr>>16), + (int)(adr&0xffff)); + /* try to continue on */ + } else { + acpi_bus_start(device); + } + } + } + } + /* Call the driver for the new device */ pci_bus_add_devices(slot->pci_bus); /* Call the drivers for the new devices subordinate to PPB */ @@ -412,6 +494,7 @@ static int disable_slot(struct hotplug_slot *bss_hotplug_slot) struct pci_dev *dev; int func; int rc; + acpi_owner_id ssdt_id = 0; /* Acquire update access to the bus */ mutex_lock(&sn_hotplug_mutex); @@ -422,6 +505,52 @@ static int disable_slot(struct hotplug_slot *bss_hotplug_slot) if (rc) goto leaving; + /* free the ACPI resources for the slot */ + if (SN_ACPI_BASE_SUPPORT() && + PCI_CONTROLLER(slot->pci_bus)->acpi_handle) { + unsigned long adr; + struct acpi_device *device; + acpi_handle phandle; + acpi_handle chandle = NULL; + acpi_handle rethandle; + acpi_status ret; + + /* Get the rootbus node pointer */ + phandle = PCI_CONTROLLER(slot->pci_bus)->acpi_handle; + + /* + * Walk the rootbus node's immediate children looking for + * the slot's device node(s). There can be more than + * one for multifunction devices. + */ + for (;;) { + rethandle = NULL; + ret = acpi_get_next_object(ACPI_TYPE_DEVICE, + phandle, chandle, + &rethandle); + + if (ret == AE_NOT_FOUND || rethandle == NULL) + break; + + chandle = rethandle; + + ret = acpi_evaluate_integer(chandle, + METHOD_NAME__ADR, + NULL, &adr); + if (ACPI_SUCCESS(ret) && + (adr>>16) == (slot->device_num + 1)) { + /* retain the owner id */ + acpi_get_id(chandle, &ssdt_id); + + ret = acpi_bus_get_device(chandle, + &device); + if (ACPI_SUCCESS(ret)) + acpi_bus_trim(device, 1); + } + } + + } + /* Free the SN resources assigned to the Linux device.*/ for (func = 0; func < 8; func++) { dev = pci_get_slot(slot->pci_bus, @@ -434,6 +563,18 @@ static int disable_slot(struct hotplug_slot *bss_hotplug_slot) } } + /* Remove the SSDT for the slot from the ACPI namespace */ + if (SN_ACPI_BASE_SUPPORT() && ssdt_id) { + acpi_status ret; + ret = acpi_unload_table_id(ssdt_id); + if (ACPI_FAILURE(ret)) { + printk(KERN_ERR "%s: acpi_unload_table_id " + "failed (0x%x) for id %d\n", + __FUNCTION__, ret, ssdt_id); + /* try to continue on */ + } + } + /* free the collected sysdata pointers */ sn_bus_free_sysdata(); -- cgit v0.10.2 From b0b7eaaf0c7aefd118d3ff8640fbed75a9fad9a1 Mon Sep 17 00:00:00 2001 From: Alexey Starikovskiy Date: Thu, 25 Jan 2007 22:39:44 -0500 Subject: ACPICA: fix gcc build warnings drivers/acpi/namespace/nsparse.c:126: warning: int format, different type arg (arg 7) drivers/acpi/tables/tbfadt.c:224: warning: unsigned int format, different type arg (arg 6) drivers/acpi/utilities/utdebug.c:184: warning: cast from pointer to integer of different size drivers/acpi/utilities/utdebug.c:184: warning: cast from pointer to integer of different size drivers/acpi/utilities/utdebug.c:197: warning: cast from pointer to integer of different size drivers/acpi/processor_idle.c:1093: warning: long long unsigned int format, u64 arg (arg 5) Signed-off-by: Len Brown diff --git a/drivers/acpi/namespace/nsparse.c b/drivers/acpi/namespace/nsparse.c index 0e57cc6..e696aa8 100644 --- a/drivers/acpi/namespace/nsparse.c +++ b/drivers/acpi/namespace/nsparse.c @@ -124,7 +124,7 @@ acpi_ns_one_complete_parse(acpi_native_uint pass_number, /* Parse the AML */ ACPI_DEBUG_PRINT((ACPI_DB_PARSE, "*PARSE* pass %d parse\n", - pass_number)); + (unsigned)pass_number)); status = acpi_ps_parse_aml(walk_state); acpi_ps_delete_parse_tree(parse_root); diff --git a/drivers/acpi/processor_idle.c b/drivers/acpi/processor_idle.c index 1d633f7..6c6751b 100644 --- a/drivers/acpi/processor_idle.c +++ b/drivers/acpi/processor_idle.c @@ -1090,7 +1090,7 @@ static int acpi_processor_power_seq_show(struct seq_file *seq, void *offset) seq_printf(seq, "latency[%03d] usage[%08d] duration[%020llu]\n", pr->power.states[i].latency, pr->power.states[i].usage, - pr->power.states[i].time); + (unsigned long long)pr->power.states[i].time); } end: diff --git a/drivers/acpi/tables/tbfadt.c b/drivers/acpi/tables/tbfadt.c index a6723a2..807c711 100644 --- a/drivers/acpi/tables/tbfadt.c +++ b/drivers/acpi/tables/tbfadt.c @@ -222,8 +222,8 @@ void acpi_tb_create_local_fadt(struct acpi_table_header *table, u32 length) */ if (length > sizeof(struct acpi_table_fadt)) { ACPI_WARNING((AE_INFO, - "FADT (revision %u) is longer than ACPI 2.0 version, truncating length 0x%X to 0x%X", - table->revision, length, + "FADT (revision %u) is longer than ACPI 2.0 version, truncating length 0x%X to 0x%zX", + table->revision, (unsigned)length, sizeof(struct acpi_table_fadt))); } diff --git a/drivers/acpi/utilities/utdebug.c b/drivers/acpi/utilities/utdebug.c index 179ad18..61ad4f2 100644 --- a/drivers/acpi/utilities/utdebug.c +++ b/drivers/acpi/utilities/utdebug.c @@ -180,8 +180,8 @@ acpi_ut_debug_print(u32 requested_debug_level, if (thread_id != acpi_gbl_prev_thread_id) { if (ACPI_LV_THREADS & acpi_dbg_level) { acpi_os_printf - ("\n**** Context Switch from TID %X to TID %X ****\n\n", - (unsigned)acpi_gbl_prev_thread_id, (unsigned)thread_id); + ("\n**** Context Switch from TID %lX to TID %lX ****\n\n", + (unsigned long)acpi_gbl_prev_thread_id, (unsigned long)thread_id); } acpi_gbl_prev_thread_id = thread_id; @@ -194,7 +194,7 @@ acpi_ut_debug_print(u32 requested_debug_level, acpi_os_printf("%8s-%04ld ", module_name, line_number); if (ACPI_LV_THREADS & acpi_dbg_level) { - acpi_os_printf("[%04X] ", (unsigned)thread_id); + acpi_os_printf("[%04lX] ", (unsigned long)thread_id); } acpi_os_printf("[%02ld] %-22.22s: ", -- cgit v0.10.2 From fe9a2f77e5ad508b18671571c0b3f6f79ea709a8 Mon Sep 17 00:00:00 2001 From: Kristen Carlson Accardi Date: Fri, 2 Feb 2007 22:33:00 -0500 Subject: ACPI: dock: check if parent is on dock When determining if a device is on a dock station, we should check the parent of the device as well. Signed-off-by: Kristen Carlson Accardi Signed-off-by: Len Brown diff --git a/drivers/acpi/dock.c b/drivers/acpi/dock.c index 90990a4..688e83a 100644 --- a/drivers/acpi/dock.c +++ b/drivers/acpi/dock.c @@ -615,20 +615,28 @@ static acpi_status find_dock_devices(acpi_handle handle, u32 lvl, void *context, void **rv) { acpi_status status; - acpi_handle tmp; + acpi_handle tmp, parent; struct dock_station *ds = context; struct dock_dependent_device *dd; status = acpi_bus_get_ejd(handle, &tmp); - if (ACPI_FAILURE(status)) - return AE_OK; + if (ACPI_FAILURE(status)) { + /* try the parent device as well */ + status = acpi_get_parent(handle, &parent); + if (ACPI_FAILURE(status)) + goto fdd_out; + /* see if parent is dependent on dock */ + status = acpi_bus_get_ejd(parent, &tmp); + if (ACPI_FAILURE(status)) + goto fdd_out; + } if (tmp == ds->handle) { dd = alloc_dock_dependent_device(handle); if (dd) add_dock_dependent_device(ds, dd); } - +fdd_out: return AE_OK; } -- cgit v0.10.2 From 01b57e73728880b787c85e27ad06c249412813b1 Mon Sep 17 00:00:00 2001 From: Kristen Carlson Accardi Date: Fri, 20 Oct 2006 14:30:25 -0700 Subject: ACPI: bay: new driver adding removable drive bay support Signed-off-by: Kristen Carlson Accardi Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index f4f000a..2caef09 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -139,6 +139,13 @@ config ACPI_DOCK help This driver adds support for ACPI controlled docking stations +config ACPI_BAY + tristate "Removable Drive Bay" + depends on EXPERIMENTAL + help + This driver adds support for ACPI controlled removable drive + bays such as the IBM ultrabay or the Dell Module Bay. + config ACPI_PROCESSOR tristate "Processor" default y diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile index bce7ca2..1a73805 100644 --- a/drivers/acpi/Makefile +++ b/drivers/acpi/Makefile @@ -43,7 +43,8 @@ obj-$(CONFIG_ACPI_BUTTON) += button.o obj-$(CONFIG_ACPI_EC) += ec.o obj-$(CONFIG_ACPI_FAN) += fan.o obj-$(CONFIG_ACPI_DOCK) += dock.o -obj-$(CONFIG_ACPI_VIDEO) += video.o +obj-$(CONFIG_ACPI_BAY) += bay.o +obj-$(CONFIG_ACPI_VIDEO) += video.o obj-$(CONFIG_ACPI_HOTKEY) += hotkey.o obj-y += pci_root.o pci_link.o pci_irq.o pci_bind.o obj-$(CONFIG_ACPI_POWER) += power.o diff --git a/drivers/acpi/bay.c b/drivers/acpi/bay.c new file mode 100644 index 0000000..1cfc0b7 --- /dev/null +++ b/drivers/acpi/bay.c @@ -0,0 +1,592 @@ +/* + * bay.c - ACPI removable drive bay driver + * + * Copyright (C) 2006 Kristen Carlson Accardi + * + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or (at + * your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + * + * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define ACPI_BAY_DRIVER_NAME "ACPI Removable Drive Bay Driver" + +ACPI_MODULE_NAME("bay") +MODULE_AUTHOR("Kristen Carlson Accardi"); +MODULE_DESCRIPTION(ACPI_BAY_DRIVER_NAME); +MODULE_LICENSE("GPL"); +#define ACPI_BAY_CLASS "bay" +#define ACPI_BAY_COMPONENT 0x10000000 +#define _COMPONENT ACPI_BAY_COMPONENT +#define bay_dprintk(h,s) {\ + char prefix[80] = {'\0'};\ + struct acpi_buffer buffer = {sizeof(prefix), prefix};\ + acpi_get_name(h, ACPI_FULL_PATHNAME, &buffer);\ + printk(KERN_DEBUG PREFIX "%s: %s\n", prefix, s); } + +static void bay_notify(acpi_handle handle, u32 event, void *data); +static int acpi_bay_add(struct acpi_device *device); +static int acpi_bay_remove(struct acpi_device *device, int type); +static int acpi_bay_match(struct acpi_device *device, + struct acpi_driver *driver); + +static struct acpi_driver acpi_bay_driver = { + .name = ACPI_BAY_DRIVER_NAME, + .class = ACPI_BAY_CLASS, + .ops = { + .add = acpi_bay_add, + .remove = acpi_bay_remove, + .match = acpi_bay_match, + }, +}; + +struct bay { + acpi_handle handle; + char *name; + struct list_head list; + struct proc_dir_entry *proc; +}; + +LIST_HEAD(drive_bays); + +static struct proc_dir_entry *acpi_bay_dir; + +/***************************************************************************** + * Drive Bay functions * + *****************************************************************************/ +/** + * is_ejectable - see if a device is ejectable + * @handle: acpi handle of the device + * + * If an acpi object has a _EJ0 method, then it is ejectable + */ +static int is_ejectable(acpi_handle handle) +{ + acpi_status status; + acpi_handle tmp; + + status = acpi_get_handle(handle, "_EJ0", &tmp); + if (ACPI_FAILURE(status)) + return 0; + return 1; +} + +/** + * bay_present - see if the bay device is present + * @bay: the drive bay + * + * execute the _STA method. + */ +static int bay_present(struct bay *bay) +{ + unsigned long sta; + acpi_status status; + + if (bay) { + status = acpi_evaluate_integer(bay->handle, "_STA", NULL, &sta); + if (ACPI_SUCCESS(status) && sta) + return 1; + } + return 0; +} + +/** + * eject_device - respond to an eject request + * @handle - the device to eject + * + * Call this devices _EJ0 method. + */ +static void eject_device(acpi_handle handle) +{ + struct acpi_object_list arg_list; + union acpi_object arg; + + bay_dprintk(handle, "Ejecting device"); + + arg_list.count = 1; + arg_list.pointer = &arg; + arg.type = ACPI_TYPE_INTEGER; + arg.integer.value = 1; + + if (ACPI_FAILURE(acpi_evaluate_object(handle, "_EJ0", + &arg_list, NULL))) + pr_debug("Failed to evaluate _EJ0!\n"); +} + + +/** + * is_ata - see if a device is an ata device + * @handle: acpi handle of the device + * + * If an acpi object has one of 4 ATA ACPI methods defined, + * then it is an ATA device + */ +static int is_ata(acpi_handle handle) +{ + acpi_handle tmp; + + if ((ACPI_SUCCESS(acpi_get_handle(handle, "_GTF", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(handle, "_GTM", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(handle, "_STM", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(handle, "_SDD", &tmp)))) + return 1; + + return 0; +} + +/** + * parent_is_ata(acpi_handle handle) + * + */ +static int parent_is_ata(acpi_handle handle) +{ + acpi_handle phandle; + + if (acpi_get_parent(handle, &phandle)) + return 0; + + return is_ata(phandle); +} + +/** + * is_ejectable_bay - see if a device is an ejectable drive bay + * @handle: acpi handle of the device + * + * If an acpi object is ejectable and has one of the ACPI ATA + * methods defined, then we can safely call it an ejectable + * drive bay + */ +static int is_ejectable_bay(acpi_handle handle) +{ + if ((is_ata(handle) || parent_is_ata(handle)) && is_ejectable(handle)) + return 1; + return 0; +} + +/** + * eject_removable_drive - try to eject this drive + * @dev : the device structure of the drive + * + * If a device is a removable drive that requires an _EJ0 method + * to be executed in order to safely remove from the system, do + * it. ATM - always returns success + */ +int eject_removable_drive(struct device *dev) +{ + acpi_handle handle = DEVICE_ACPI_HANDLE(dev); + + if (handle) { + bay_dprintk(handle, "Got device handle"); + if (is_ejectable_bay(handle)) + eject_device(handle); + } else { + printk("No acpi handle for device\n"); + } + + /* should I return an error code? */ + return 0; +} +EXPORT_SYMBOL_GPL(eject_removable_drive); + +static int acpi_bay_add(struct acpi_device *device) +{ + bay_dprintk(device->handle, "adding bay device"); + strcpy(acpi_device_name(device), "Dockable Bay"); + strcpy(acpi_device_class(device), "bay"); + return 0; +} + +static int acpi_bay_status_seq_show(struct seq_file *seq, void *offset) +{ + struct bay *bay = (struct bay *)seq->private; + + if (!bay) + return 0; + + if (bay_present(bay)) + seq_printf(seq, "present\n"); + else + seq_printf(seq, "removed\n"); + + return 0; +} + +static ssize_t +acpi_bay_write_eject(struct file *file, + const char __user * buffer, + size_t count, loff_t * data) +{ + struct seq_file *m = (struct seq_file *)file->private_data; + struct bay *bay = (struct bay *)m->private; + char str[12] = { 0 }; + u32 state = 0; + + /* FIXME - our only valid value here is 1 */ + if (!bay || count + 1 > sizeof str) + return -EINVAL; + + if (copy_from_user(str, buffer, count)) + return -EFAULT; + + str[count] = 0; + state = simple_strtoul(str, NULL, 0); + if (state) + eject_device(bay->handle); + + return count; +} + +static int +acpi_bay_status_open_fs(struct inode *inode, struct file *file) +{ + return single_open(file, acpi_bay_status_seq_show, + PDE(inode)->data); +} + +static int +acpi_bay_eject_open_fs(struct inode *inode, struct file *file) +{ + return single_open(file, acpi_bay_status_seq_show, + PDE(inode)->data); +} + +static struct file_operations acpi_bay_status_fops = { + .open = acpi_bay_status_open_fs, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, +}; + +static struct file_operations acpi_bay_eject_fops = { + .open = acpi_bay_eject_open_fs, + .read = seq_read, + .write = acpi_bay_write_eject, + .llseek = seq_lseek, + .release = single_release, +}; +#if 0 +static struct file_operations acpi_bay_insert_fops = { + .open = acpi_bay_insert_open_fs, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, +}; +#endif +static int acpi_bay_add_fs(struct bay *bay) +{ + struct proc_dir_entry *entry = NULL; + + if (!bay) + return -EINVAL; + + /* + * create a proc entry for this device + * we need to do this a little bit differently than normal + * acpi device drivers because our device may not be present + * at the moment, and therefore we have no acpi_device struct + */ + + bay->proc = proc_mkdir(bay->name, acpi_bay_dir); + + /* 'status' [R] */ + entry = create_proc_entry("status", + S_IRUGO, bay->proc); + if (!entry) + return -EIO; + else { + entry->proc_fops = &acpi_bay_status_fops; + entry->data = bay; + entry->owner = THIS_MODULE; + } + /* 'eject' [W] */ + entry = create_proc_entry("eject", + S_IWUGO, bay->proc); + if (!entry) + return -EIO; + else { + entry->proc_fops = &acpi_bay_eject_fops; + entry->data = bay; + entry->owner = THIS_MODULE; + } +#if 0 + /* 'insert' [W] */ + entry = create_proc_entry("insert", + S_IWUGO, bay->proc); + if (!entry) + return -EIO; + else { + entry->proc_fops = &acpi_bay_insert_fops; + entry->data = bay; + entry->owner = THIS_MODULE; + } +#endif + return 0; +} + +static void acpi_bay_remove_fs(struct bay *bay) +{ + if (!bay) + return; + + if (bay->proc) { + remove_proc_entry("status", bay->proc); + remove_proc_entry("eject", bay->proc); +#if 0 + remove_proc_entry("insert", bay->proc); +#endif + remove_proc_entry(bay->name, acpi_bay_dir); + bay->proc = NULL; + } +} + +static int bay_is_dock_device(acpi_handle handle) +{ + acpi_handle parent; + + acpi_get_parent(handle, &parent); + + /* if the device or it's parent is dependent on the + * dock, then we are a dock device + */ + return (is_dock_device(handle) || is_dock_device(parent)); +} + +static int bay_add(acpi_handle handle) +{ + acpi_status status; + struct bay *new_bay; + struct acpi_buffer nbuffer = {ACPI_ALLOCATE_BUFFER, NULL}; + acpi_get_name(handle, ACPI_FULL_PATHNAME, &nbuffer); + + bay_dprintk(handle, "Adding notify handler"); + + /* + * if this is the first bay device found, make the root + * proc entry + */ + if (acpi_bay_dir == NULL) + acpi_bay_dir = proc_mkdir(ACPI_BAY_CLASS, acpi_root_dir); + + /* + * Initialize bay device structure + */ + new_bay = kmalloc(GFP_ATOMIC, sizeof(*new_bay)); + INIT_LIST_HEAD(&new_bay->list); + new_bay->handle = handle; + new_bay->name = (char *)nbuffer.pointer; + list_add(&new_bay->list, &drive_bays); + acpi_bay_add_fs(new_bay); + + /* register for events on this device */ + status = acpi_install_notify_handler(handle, ACPI_SYSTEM_NOTIFY, + bay_notify, new_bay); + if (ACPI_FAILURE(status)) { + printk(KERN_ERR PREFIX "Error installing bay notify handler\n"); + } + + /* if we are on a dock station, we should register for dock + * notifications. + */ + if (bay_is_dock_device(handle)) { + bay_dprintk(handle, "Is dependent on dock\n"); + register_hotplug_dock_device(handle, bay_notify, new_bay); + } + printk(KERN_INFO PREFIX "Bay [%s] Added\n", new_bay->name); + return 0; +} + +static int acpi_bay_remove(struct acpi_device *device, int type) +{ + /*** FIXME: do something here */ + return 0; +} + +static int acpi_bay_match(struct acpi_device *device, + struct acpi_driver *driver) +{ + if (!device || !driver) + return -EINVAL; + + if (is_ejectable_bay(device->handle)) { + bay_dprintk(device->handle, "matching bay device"); + return 0; + } + + return -ENODEV; +} + +/** + * bay_create_acpi_device - add new devices to acpi + * @handle - handle of the device to add + * + * This function will create a new acpi_device for the given + * handle if one does not exist already. This should cause + * acpi to scan for drivers for the given devices, and call + * matching driver's add routine. + * + * Returns a pointer to the acpi_device corresponding to the handle. + */ +static struct acpi_device * bay_create_acpi_device(acpi_handle handle) +{ + struct acpi_device *device = NULL; + struct acpi_device *parent_device; + acpi_handle parent; + int ret; + + bay_dprintk(handle, "Trying to get device"); + if (acpi_bus_get_device(handle, &device)) { + /* + * no device created for this object, + * so we should create one. + */ + bay_dprintk(handle, "No device for handle"); + acpi_get_parent(handle, &parent); + if (acpi_bus_get_device(parent, &parent_device)) + parent_device = NULL; + + ret = acpi_bus_add(&device, parent_device, handle, + ACPI_BUS_TYPE_DEVICE); + if (ret) { + pr_debug("error adding bus, %x\n", + -ret); + return NULL; + } + } + return device; +} + +/** + * bay_notify - act upon an acpi bay notification + * @handle: the bay handle + * @event: the acpi event + * @data: our driver data struct + * + */ +static void bay_notify(acpi_handle handle, u32 event, void *data) +{ + struct acpi_device *dev; + struct bay *bay = data; + + bay_dprintk(handle, "Bay event"); + + switch(event) { + case ACPI_NOTIFY_BUS_CHECK: + printk("Bus Check\n"); + case ACPI_NOTIFY_DEVICE_CHECK: + printk("Device Check\n"); + dev = bay_create_acpi_device(handle); + if (dev) + acpi_bus_generate_event(dev, event, 0); + else + printk("No device for generating event\n"); + /* wouldn't it be a good idea to just rescan SATA + * right here? + */ + break; + case ACPI_NOTIFY_EJECT_REQUEST: + printk("Eject request\n"); + dev = bay_create_acpi_device(handle); + if (dev) + acpi_bus_generate_event(dev, event, 0); + else + printk("No device for generating eventn"); + + /* wouldn't it be a good idea to just call the + * eject_device here if we were a SATA device? + */ + break; + default: + printk("unknown event %d\n", event); + } +} + +static acpi_status +find_bay(acpi_handle handle, u32 lvl, void *context, void **rv) +{ + int *count = (int *)context; + + /* + * there could be more than one ejectable bay. + * so, just return AE_OK always so that every object + * will be checked. + */ + if (is_ejectable_bay(handle)) { + bay_dprintk(handle, "found ejectable bay"); + bay_add(handle); + (*count)++; + } + return AE_OK; +} + +static int __init bay_init(void) +{ + int bays = 0; + + acpi_bay_dir = NULL; + INIT_LIST_HEAD(&drive_bays); + + /* look for dockable drive bays */ + acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT, + ACPI_UINT32_MAX, find_bay, &bays, NULL); + + if (bays) { + if ((acpi_bus_register_driver(&acpi_bay_driver) < 0)) { + printk(KERN_ERR "Unable to register bay driver\n"); + if (acpi_bay_dir) + remove_proc_entry(ACPI_BAY_CLASS, + acpi_root_dir); + } + } + + if (!bays) + return -ENODEV; + + return 0; +} + +static void __exit bay_exit(void) +{ + struct bay *bay, *tmp; + + list_for_each_entry_safe(bay, tmp, &drive_bays, list) { + if (is_dock_device(bay->handle)) + unregister_hotplug_dock_device(bay->handle); + acpi_bay_remove_fs(bay); + acpi_remove_notify_handler(bay->handle, ACPI_SYSTEM_NOTIFY, + bay_notify); + kfree(bay->name); + kfree(bay); + } + + if (acpi_bay_dir) + remove_proc_entry(ACPI_BAY_CLASS, acpi_root_dir); + + acpi_bus_unregister_driver(&acpi_bay_driver); +} + +postcore_initcall(bay_init); +module_exit(bay_exit); + -- cgit v0.10.2 From 5447cbb278fd01c402180ab1e820b95101e782fa Mon Sep 17 00:00:00 2001 From: Len Brown Date: Sat, 21 Oct 2006 01:15:41 -0400 Subject: ACPI: bay: delete unused variable MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit drivers/acpi/bay.c: In function ‘bay_notify’: drivers/acpi/bay.c:491: warning: unused variable ‘bay’ Signed-off-by: Len Brown diff --git a/drivers/acpi/bay.c b/drivers/acpi/bay.c index 1cfc0b7..412590d 100644 --- a/drivers/acpi/bay.c +++ b/drivers/acpi/bay.c @@ -488,7 +488,6 @@ static struct acpi_device * bay_create_acpi_device(acpi_handle handle) static void bay_notify(acpi_handle handle, u32 event, void *data) { struct acpi_device *dev; - struct bay *bay = data; bay_dprintk(handle, "Bay event"); -- cgit v0.10.2 From e9dd85e5bdff2a3981dfaa55869ba920e985ea8a Mon Sep 17 00:00:00 2001 From: Kristen Carlson Accardi Date: Mon, 18 Dec 2006 18:06:00 -0500 Subject: ACPI: bay: remove prototype procfs code Remove all the procfs related code. Signed-off-by: Kristen Carlson Accardi Signed-off-by: Len Brown diff --git a/drivers/acpi/bay.c b/drivers/acpi/bay.c index 412590d..0c0a620 100644 --- a/drivers/acpi/bay.c +++ b/drivers/acpi/bay.c @@ -28,7 +28,6 @@ #include #include #include -#include #include #include @@ -67,12 +66,10 @@ struct bay { acpi_handle handle; char *name; struct list_head list; - struct proc_dir_entry *proc; }; LIST_HEAD(drive_bays); -static struct proc_dir_entry *acpi_bay_dir; /***************************************************************************** * Drive Bay functions * @@ -219,147 +216,16 @@ static int acpi_bay_add(struct acpi_device *device) return 0; } -static int acpi_bay_status_seq_show(struct seq_file *seq, void *offset) -{ - struct bay *bay = (struct bay *)seq->private; - - if (!bay) - return 0; - - if (bay_present(bay)) - seq_printf(seq, "present\n"); - else - seq_printf(seq, "removed\n"); - - return 0; -} - -static ssize_t -acpi_bay_write_eject(struct file *file, - const char __user * buffer, - size_t count, loff_t * data) -{ - struct seq_file *m = (struct seq_file *)file->private_data; - struct bay *bay = (struct bay *)m->private; - char str[12] = { 0 }; - u32 state = 0; - - /* FIXME - our only valid value here is 1 */ - if (!bay || count + 1 > sizeof str) - return -EINVAL; - - if (copy_from_user(str, buffer, count)) - return -EFAULT; - - str[count] = 0; - state = simple_strtoul(str, NULL, 0); - if (state) - eject_device(bay->handle); - - return count; -} - -static int -acpi_bay_status_open_fs(struct inode *inode, struct file *file) -{ - return single_open(file, acpi_bay_status_seq_show, - PDE(inode)->data); -} - -static int -acpi_bay_eject_open_fs(struct inode *inode, struct file *file) -{ - return single_open(file, acpi_bay_status_seq_show, - PDE(inode)->data); -} - -static struct file_operations acpi_bay_status_fops = { - .open = acpi_bay_status_open_fs, - .read = seq_read, - .llseek = seq_lseek, - .release = single_release, -}; - -static struct file_operations acpi_bay_eject_fops = { - .open = acpi_bay_eject_open_fs, - .read = seq_read, - .write = acpi_bay_write_eject, - .llseek = seq_lseek, - .release = single_release, -}; -#if 0 -static struct file_operations acpi_bay_insert_fops = { - .open = acpi_bay_insert_open_fs, - .read = seq_read, - .llseek = seq_lseek, - .release = single_release, -}; -#endif static int acpi_bay_add_fs(struct bay *bay) { - struct proc_dir_entry *entry = NULL; - if (!bay) return -EINVAL; - - /* - * create a proc entry for this device - * we need to do this a little bit differently than normal - * acpi device drivers because our device may not be present - * at the moment, and therefore we have no acpi_device struct - */ - - bay->proc = proc_mkdir(bay->name, acpi_bay_dir); - - /* 'status' [R] */ - entry = create_proc_entry("status", - S_IRUGO, bay->proc); - if (!entry) - return -EIO; - else { - entry->proc_fops = &acpi_bay_status_fops; - entry->data = bay; - entry->owner = THIS_MODULE; - } - /* 'eject' [W] */ - entry = create_proc_entry("eject", - S_IWUGO, bay->proc); - if (!entry) - return -EIO; - else { - entry->proc_fops = &acpi_bay_eject_fops; - entry->data = bay; - entry->owner = THIS_MODULE; - } -#if 0 - /* 'insert' [W] */ - entry = create_proc_entry("insert", - S_IWUGO, bay->proc); - if (!entry) - return -EIO; - else { - entry->proc_fops = &acpi_bay_insert_fops; - entry->data = bay; - entry->owner = THIS_MODULE; - } -#endif - return 0; } static void acpi_bay_remove_fs(struct bay *bay) { if (!bay) return; - - if (bay->proc) { - remove_proc_entry("status", bay->proc); - remove_proc_entry("eject", bay->proc); -#if 0 - remove_proc_entry("insert", bay->proc); -#endif - remove_proc_entry(bay->name, acpi_bay_dir); - bay->proc = NULL; - } } static int bay_is_dock_device(acpi_handle handle) @@ -384,13 +250,6 @@ static int bay_add(acpi_handle handle) bay_dprintk(handle, "Adding notify handler"); /* - * if this is the first bay device found, make the root - * proc entry - */ - if (acpi_bay_dir == NULL) - acpi_bay_dir = proc_mkdir(ACPI_BAY_CLASS, acpi_root_dir); - - /* * Initialize bay device structure */ new_bay = kmalloc(GFP_ATOMIC, sizeof(*new_bay)); @@ -544,21 +403,15 @@ static int __init bay_init(void) { int bays = 0; - acpi_bay_dir = NULL; INIT_LIST_HEAD(&drive_bays); /* look for dockable drive bays */ acpi_walk_namespace(ACPI_TYPE_DEVICE, ACPI_ROOT_OBJECT, ACPI_UINT32_MAX, find_bay, &bays, NULL); - if (bays) { - if ((acpi_bus_register_driver(&acpi_bay_driver) < 0)) { + if (bays) + if ((acpi_bus_register_driver(&acpi_bay_driver) < 0)) printk(KERN_ERR "Unable to register bay driver\n"); - if (acpi_bay_dir) - remove_proc_entry(ACPI_BAY_CLASS, - acpi_root_dir); - } - } if (!bays) return -ENODEV; @@ -580,9 +433,6 @@ static void __exit bay_exit(void) kfree(bay); } - if (acpi_bay_dir) - remove_proc_entry(ACPI_BAY_CLASS, acpi_root_dir); - acpi_bus_unregister_driver(&acpi_bay_driver); } -- cgit v0.10.2 From 2b167c01190b647c976e7fab312f2e3d3b3a785f Mon Sep 17 00:00:00 2001 From: Kristen Carlson Accardi Date: Mon, 18 Dec 2006 18:07:00 -0500 Subject: ACPI: bay: make bay a platform driver Convert the bay driver to be a platform driver, so that we can have sysfs entries. Signed-off-by: Kristen Carlson Accardi Signed-off-by: Len Brown diff --git a/drivers/acpi/bay.c b/drivers/acpi/bay.c index 0c0a620..3f0ae7d 100644 --- a/drivers/acpi/bay.c +++ b/drivers/acpi/bay.c @@ -30,6 +30,7 @@ #include #include #include +#include #define ACPI_BAY_DRIVER_NAME "ACPI Removable Drive Bay Driver" @@ -45,7 +46,6 @@ MODULE_LICENSE("GPL"); struct acpi_buffer buffer = {sizeof(prefix), prefix};\ acpi_get_name(h, ACPI_FULL_PATHNAME, &buffer);\ printk(KERN_DEBUG PREFIX "%s: %s\n", prefix, s); } - static void bay_notify(acpi_handle handle, u32 event, void *data); static int acpi_bay_add(struct acpi_device *device); static int acpi_bay_remove(struct acpi_device *device, int type); @@ -66,6 +66,7 @@ struct bay { acpi_handle handle; char *name; struct list_head list; + struct platform_device *pdev; }; LIST_HEAD(drive_bays); @@ -133,6 +134,33 @@ static void eject_device(acpi_handle handle) pr_debug("Failed to evaluate _EJ0!\n"); } +/* + * show_present - read method for "present" file in sysfs + */ +static ssize_t show_present(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct bay *bay = dev_get_drvdata(dev); + return snprintf(buf, PAGE_SIZE, "%d\n", bay_present(bay)); + +} +DEVICE_ATTR(present, S_IRUGO, show_present, NULL); + +/* + * write_eject - write method for "eject" file in sysfs + */ +static ssize_t write_eject(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + struct bay *bay = dev_get_drvdata(dev); + + if (!count) + return -EINVAL; + + eject_device(bay->handle); + return count; +} +DEVICE_ATTR(eject, S_IWUSR, NULL, write_eject); /** * is_ata - see if a device is an ata device @@ -218,14 +246,31 @@ static int acpi_bay_add(struct acpi_device *device) static int acpi_bay_add_fs(struct bay *bay) { - if (!bay) - return -EINVAL; + int ret; + struct device *dev = &bay->pdev->dev; + + ret = device_create_file(dev, &dev_attr_present); + if (ret) + goto add_fs_err; + ret = device_create_file(dev, &dev_attr_eject); + if (ret) { + device_remove_file(dev, &dev_attr_present); + goto add_fs_err; + } + return 0; + + add_fs_err: + bay_dprintk(bay->handle, "Error adding sysfs files\n"); + return ret; } static void acpi_bay_remove_fs(struct bay *bay) { - if (!bay) - return; + struct device *dev = &bay->pdev->dev; + + /* cleanup sysfs */ + device_remove_file(dev, &dev_attr_present); + device_remove_file(dev, &dev_attr_eject); } static int bay_is_dock_device(acpi_handle handle) @@ -240,10 +285,11 @@ static int bay_is_dock_device(acpi_handle handle) return (is_dock_device(handle) || is_dock_device(parent)); } -static int bay_add(acpi_handle handle) +static int bay_add(acpi_handle handle, int id) { acpi_status status; struct bay *new_bay; + struct platform_device *pdev; struct acpi_buffer nbuffer = {ACPI_ALLOCATE_BUFFER, NULL}; acpi_get_name(handle, ACPI_FULL_PATHNAME, &nbuffer); @@ -252,12 +298,24 @@ static int bay_add(acpi_handle handle) /* * Initialize bay device structure */ - new_bay = kmalloc(GFP_ATOMIC, sizeof(*new_bay)); + new_bay = kzalloc(GFP_ATOMIC, sizeof(*new_bay)); INIT_LIST_HEAD(&new_bay->list); new_bay->handle = handle; new_bay->name = (char *)nbuffer.pointer; - list_add(&new_bay->list, &drive_bays); - acpi_bay_add_fs(new_bay); + + /* initialize platform device stuff */ + pdev = platform_device_register_simple(ACPI_BAY_CLASS, id, NULL, 0); + if (pdev == NULL) { + printk(KERN_ERR PREFIX "Error registering bay device\n"); + goto bay_add_err; + } + new_bay->pdev = pdev; + platform_set_drvdata(pdev, new_bay); + + if (acpi_bay_add_fs(new_bay)) { + platform_device_unregister(new_bay->pdev); + goto bay_add_err; + } /* register for events on this device */ status = acpi_install_notify_handler(handle, ACPI_SYSTEM_NOTIFY, @@ -273,8 +331,14 @@ static int bay_add(acpi_handle handle) bay_dprintk(handle, "Is dependent on dock\n"); register_hotplug_dock_device(handle, bay_notify, new_bay); } + list_add(&new_bay->list, &drive_bays); printk(KERN_INFO PREFIX "Bay [%s] Added\n", new_bay->name); return 0; + +bay_add_err: + kfree(new_bay->name); + kfree(new_bay); + return -ENODEV; } static int acpi_bay_remove(struct acpi_device *device, int type) @@ -393,8 +457,8 @@ find_bay(acpi_handle handle, u32 lvl, void *context, void **rv) */ if (is_ejectable_bay(handle)) { bay_dprintk(handle, "found ejectable bay"); - bay_add(handle); - (*count)++; + if (!bay_add(handle, *count)) + (*count)++; } return AE_OK; } @@ -429,6 +493,7 @@ static void __exit bay_exit(void) acpi_bay_remove_fs(bay); acpi_remove_notify_handler(bay->handle, ACPI_SYSTEM_NOTIFY, bay_notify); + platform_device_unregister(bay->pdev); kfree(bay->name); kfree(bay); } -- cgit v0.10.2 From 5d22e1e83aac1f81f948ac8bff281487c11cc967 Mon Sep 17 00:00:00 2001 From: Adrian Bunk Date: Mon, 4 Dec 2006 14:49:39 -0800 Subject: ACPI: bay: make drive_bays static Signed-off-by: Adrian Bunk Signed-off-by: Andrew Morton Signed-off-by: Len Brown diff --git a/drivers/acpi/bay.c b/drivers/acpi/bay.c index 3f0ae7d..aa1b131 100644 --- a/drivers/acpi/bay.c +++ b/drivers/acpi/bay.c @@ -69,7 +69,7 @@ struct bay { struct platform_device *pdev; }; -LIST_HEAD(drive_bays); +static LIST_HEAD(drive_bays); /***************************************************************************** -- cgit v0.10.2 From 0ed1e38d513ea683ce125e698dd41d31441e0e8c Mon Sep 17 00:00:00 2001 From: Len Brown Date: Fri, 2 Feb 2007 22:39:16 -0500 Subject: ACPI: bay: new driver is EXPERIMENTAL Signed-off-by: Len Brown diff --git a/drivers/acpi/Kconfig b/drivers/acpi/Kconfig index 2caef09..b4bb000 100644 --- a/drivers/acpi/Kconfig +++ b/drivers/acpi/Kconfig @@ -140,7 +140,7 @@ config ACPI_DOCK This driver adds support for ACPI controlled docking stations config ACPI_BAY - tristate "Removable Drive Bay" + tristate "Removable Drive Bay (EXPERIMENTAL)" depends on EXPERIMENTAL help This driver adds support for ACPI controlled removable drive -- cgit v0.10.2 From 547352660506ab99d6b0bad58dea495bf3718cee Mon Sep 17 00:00:00 2001 From: Zhang Rui Date: Thu, 11 Jan 2007 02:09:09 -0500 Subject: ACPI: bay: Convert ACPI Bay driver to be compatible with sysfs update. Set fake hid for ejectable drive bay. Match bay devices by checking the hid. Remove .match method of Bay driver. Signed-off-by: Zhang Rui Signed-off-by: Len Brown diff --git a/drivers/acpi/bay.c b/drivers/acpi/bay.c index aa1b131..667fa1d 100644 --- a/drivers/acpi/bay.c +++ b/drivers/acpi/bay.c @@ -49,16 +49,14 @@ MODULE_LICENSE("GPL"); static void bay_notify(acpi_handle handle, u32 event, void *data); static int acpi_bay_add(struct acpi_device *device); static int acpi_bay_remove(struct acpi_device *device, int type); -static int acpi_bay_match(struct acpi_device *device, - struct acpi_driver *driver); static struct acpi_driver acpi_bay_driver = { .name = ACPI_BAY_DRIVER_NAME, .class = ACPI_BAY_CLASS, + .ids = ACPI_BAY_HID, .ops = { .add = acpi_bay_add, .remove = acpi_bay_remove, - .match = acpi_bay_match, }, }; @@ -347,20 +345,6 @@ static int acpi_bay_remove(struct acpi_device *device, int type) return 0; } -static int acpi_bay_match(struct acpi_device *device, - struct acpi_driver *driver) -{ - if (!device || !driver) - return -EINVAL; - - if (is_ejectable_bay(device->handle)) { - bay_dprintk(device->handle, "matching bay device"); - return 0; - } - - return -ENODEV; -} - /** * bay_create_acpi_device - add new devices to acpi * @handle - handle of the device to add diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 5049230..0a13d95 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -837,6 +837,42 @@ acpi_video_bus_match(struct acpi_device *device) return -ENODEV; } +/* + * acpi_bay_match - see if a device is an ejectable driver bay + * + * If an acpi object is ejectable and has one of the ACPI ATA methods defined, + * then we can safely call it an ejectable drive bay + */ +static int acpi_bay_match(struct acpi_device *device){ + acpi_status status; + acpi_handle handle; + acpi_handle tmp; + acpi_handle phandle; + + handle = device->handle; + + status = acpi_get_handle(handle, "_EJ0", &tmp); + if (ACPI_FAILURE(status)) + return -ENODEV; + + if ((ACPI_SUCCESS(acpi_get_handle(handle, "_GTF", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(handle, "_GTM", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(handle, "_STM", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(handle, "_SDD", &tmp)))) + return 0; + + if (acpi_get_parent(handle, &phandle)) + return -ENODEV; + + if ((ACPI_SUCCESS(acpi_get_handle(phandle, "_GTF", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(phandle, "_GTM", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(phandle, "_STM", &tmp))) || + (ACPI_SUCCESS(acpi_get_handle(phandle, "_SDD", &tmp)))) + return 0; + + return -ENODEV; +} + static void acpi_device_set_id(struct acpi_device *device, struct acpi_device *parent, acpi_handle handle, int type) @@ -872,6 +908,10 @@ static void acpi_device_set_id(struct acpi_device *device, status = acpi_video_bus_match(device); if(ACPI_SUCCESS(status)) hid = ACPI_VIDEO_HID; + + status = acpi_bay_match(device); + if (ACPI_SUCCESS(status)) + hid = ACPI_BAY_HID; } break; case ACPI_BUS_TYPE_POWER: -- cgit v0.10.2 From 894d79bedd8b48fe838083f2d2a42ac09817c530 Mon Sep 17 00:00:00 2001 From: Len Brown Date: Sat, 3 Feb 2007 02:13:53 -0500 Subject: asus-laptop: merge with ACPICA table update No longer need a buffer for a copy of the DSDT, just a pointer to the mapped table. Signed-off-by: Len Brown diff --git a/drivers/misc/asus-laptop.c b/drivers/misc/asus-laptop.c index b624350..861c399 100644 --- a/drivers/misc/asus-laptop.c +++ b/drivers/misc/asus-laptop.c @@ -777,7 +777,6 @@ static int asus_handle_init(char *name, acpi_handle * handle, static int asus_hotk_get_info(void) { struct acpi_buffer buffer = { ACPI_ALLOCATE_BUFFER, NULL }; - struct acpi_buffer dsdt = { ACPI_ALLOCATE_BUFFER, NULL }; union acpi_object *model = NULL; int bsts_result, hwrs_result; char *string = NULL; @@ -791,11 +790,9 @@ static int asus_hotk_get_info(void) * HID), this bit will be moved. A global variable asus_info contains * the DSDT header. */ - status = acpi_get_table(ACPI_TABLE_ID_DSDT, 1, &dsdt); + status = acpi_get_table(ACPI_SIG_DSDT, 1, &asus_info); if (ACPI_FAILURE(status)) printk(ASUS_WARNING "Couldn't get the DSDT table header\n"); - else - asus_info = dsdt.pointer; /* We have to write 0 on init this far for all ASUS models */ if (!write_acpi_int(hotk->handle, "INIT", 0, &buffer)) { @@ -1014,8 +1011,6 @@ static void __exit asus_laptop_exit(void) sysfs_remove_group(&asuspf_device->dev.kobj, &asuspf_attribute_group); platform_device_unregister(asuspf_device); platform_driver_unregister(&asuspf_driver); - - kfree(asus_info); } static int asus_backlight_init(struct device *dev) -- cgit v0.10.2 From 03c6d130f690dba46387480de80acf458a6fd14c Mon Sep 17 00:00:00 2001 From: Len Brown Date: Tue, 6 Feb 2007 15:28:23 -0500 Subject: ACPICA: reduce table header messages to fit within 80 columns Signed-off-by: Len Brown diff --git a/drivers/acpi/tables/tbutils.c b/drivers/acpi/tables/tbutils.c index 4a2f99e..1da64b4 100644 --- a/drivers/acpi/tables/tbutils.c +++ b/drivers/acpi/tables/tbutils.c @@ -97,15 +97,15 @@ acpi_tb_print_table_header(acpi_physical_address address, /* FACS only has signature and length fields of common table header */ - ACPI_INFO((AE_INFO, "%4.4s @ 0x%p/0x%04X", - header->signature, ACPI_CAST_PTR(void, address), + ACPI_INFO((AE_INFO, "%4.4s %08lX, %04X", + header->signature, (unsigned long)address, header->length)); } else if (ACPI_COMPARE_NAME(header->signature, ACPI_SIG_RSDP)) { /* RSDP has no common fields */ - ACPI_INFO((AE_INFO, "RSDP @ 0x%p/0x%04X (v%3.3d %6.6s)", - ACPI_CAST_PTR(void, address), + ACPI_INFO((AE_INFO, "RSDP %08lX, %04X (r%d %6.6s)", + (unsigned long)address, (ACPI_CAST_PTR(struct acpi_table_rsdp, header)-> revision > 0) ? ACPI_CAST_PTR(struct acpi_table_rsdp, @@ -118,8 +118,8 @@ acpi_tb_print_table_header(acpi_physical_address address, /* Standard ACPI table with full common header */ ACPI_INFO((AE_INFO, - "%4.4s @ 0x%p/0x%04X (v%3.3d %6.6s %8.8s 0x%08X %4.4s 0x%08X)", - header->signature, ACPI_CAST_PTR(void, address), + "%4.4s %08lX, %04X (r%d %6.6s %8.8s %8X %4.4s %8X)", + header->signature, (unsigned long)address, header->length, header->revision, header->oem_id, header->oem_table_id, header->oem_revision, header->asl_compiler_id, -- cgit v0.10.2