X-Git-Url: http://ftp.safe.ca/?a=blobdiff_plain;f=drivers%2Fpci%2Fpci-acpi.c;h=e9e37abe1f76447510d9ad9857e8f481a677696e;hb=af36d7f0df56de3e3e4bbfb15d0915097ecb8cab;hp=f94c86fbc6695cb0e8662d253c23341c3977559f;hpb=84df749f364209c9623304b7a94ddb954dc343bb;p=safe%2Fjmp%2Flinux-2.6 diff --git a/drivers/pci/pci-acpi.c b/drivers/pci/pci-acpi.c index f94c86f..e9e37ab 100644 --- a/drivers/pci/pci-acpi.c +++ b/drivers/pci/pci-acpi.c @@ -17,6 +17,7 @@ #include #include +#include "pci.h" static u32 ctrlset_buf[3] = {0, 0, 0}; static u32 global_ctrlsets = 0; @@ -209,6 +210,56 @@ acpi_status pci_osc_control_set(u32 flags) } EXPORT_SYMBOL(pci_osc_control_set); +/* + * _SxD returns the D-state with the highest power + * (lowest D-state number) supported in the S-state "x". + * + * If the devices does not have a _PRW + * (Power Resources for Wake) supporting system wakeup from "x" + * then the OS is free to choose a lower power (higher number + * D-state) than the return value from _SxD. + * + * But if _PRW is enabled at S-state "x", the OS + * must not choose a power lower than _SxD -- + * unless the device has an _SxW method specifying + * the lowest power (highest D-state number) the device + * may enter while still able to wake the system. + * + * ie. depending on global OS policy: + * + * if (_PRW at S-state x) + * choose from highest power _SxD to lowest power _SxW + * else // no _PRW at S-state x + * choose highest power _SxD or any lower power + * + * currently we simply return _SxD, if present. + */ + +static int acpi_pci_choose_state(struct pci_dev *pdev, pm_message_t state) +{ + /* TBD */ + + return -ENODEV; +} + +static int acpi_pci_set_power_state(struct pci_dev *dev, pci_power_t state) +{ + acpi_handle handle = DEVICE_ACPI_HANDLE(&dev->dev); + static int state_conv[] = { + [0] = 0, + [1] = 1, + [2] = 2, + [3] = 3, + [4] = 3 + }; + int acpi_state = state_conv[(int __force) state]; + + if (!handle) + return -ENODEV; + return acpi_bus_set_power(handle, acpi_state); +} + + /* ACPI bus type */ static int pci_acpi_find_device(struct device *dev, acpi_handle *handle) { @@ -255,6 +306,8 @@ static int __init pci_acpi_init(void) ret = register_acpi_bus_type(&pci_acpi_bus); if (ret) return 0; + platform_pci_choose_state = acpi_pci_choose_state; + platform_pci_set_power_state = acpi_pci_set_power_state; return 0; } arch_initcall(pci_acpi_init);