Message ID | 1416290291-5802-1-git-send-email-Ken.Xue@amd.com (mailing list archive) |
---|---|
State | Changes Requested, archived |
Headers | show |
DQpPbiBUdWVzZGF5LCBOb3ZlbWJlciAxOCwgMjAxNCAwMTo1ODoxMSBQTSBLZW4gWHVlIHdyb3Rl Og0KPiBUaGlzIG5ldyBmZWF0dXJlIGlzIHRvIGludGVycHJldCBBTUQgc3BlY2lmaWMgQUNQSSBk ZXZpY2UgdG8gcGxhdGZvcm0gDQo+IGRldmljZSBzdWNoIGFzIEkyQywgVUFSVCBmb3VuZCBvbiBB TUQgQ1ogYW5kIGxhdGVyIGNoaXBzZXRzLiBJdCBpcyANCj4gYmFzZWQgb24gZXhhbXBsZSBJTlRF TCBMUFNTLiBOb3csIGl0IGNhbiBzdXBwb3J0IEFNRCBJMkMgJiBVQVJULg0KPiANCj4gU2lnbmVk LW9mZi1ieTogS2VuIFh1ZSA8S2VuLlh1ZUBhbWQuY29tPg0KPiBTaWduZWQtb2ZmLWJ5OiBKZWZm IFd1IDxKZWZmLld1QGFtZC5jb20+DQoNCkdlbmVyYWxseSBzcGVha2luZywgdGhpcyBzZWVtcyB0 byBkdXBsaWNhdGUgbXVjaCBjb2RlIGZyb20gYWNwaV9scHNzIHdoaWNoIHNob3VsZCBiZSByZS11 c2VkIGluc3RlYWQuICBXaGF0IGFib3V0IG1vdmluZyB0aGUgY29kZSB0aGF0IHdpbGwgYmUgY29t bW9uIGJldHdlZW4gYWNwaV9scHNzIGFuZCB0aGUgbmV3IGRyaXZlciBpbnRvIGEgbmV3IGZpbGUg KHNheSBhY3BpX3NvYy5jKT8NCg0KQWxzbywgeW91IG5lZWQgdG8gYXZvaWQgYXV0b21hdGljIGNy ZWF0aW9uIG9mIHBsYXRmb3JtIGRldmljZXMgd2hlbiAhWDg2X0FNRF9QTEFURk9STV9ERVZJQ0Ug aW4gYW5hbG9neSB3aXRoIHdoYXQgYWNwaV9scHNzIGRvZXMsIG9yIGJhZCB0aGluZ3Mgd2lsbCBo YXBwZW4uDQoNCltrZW5dIHNvdW5kcyBmYWlyIGVub3VnaC4gIExldCBtZSB0YWtlIGFjdGlvbiB0 byBtZXJnZSBkcml2ZXJzIHRvIGFjcGlfc29jLmMgPyBvciB5b3UgaGF2ZSBvdGhlciBwbGFuPw0K DQpbLi4uXQ0K -- To unsubscribe from this list: send the line "unsubscribe linux-acpi" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On Tuesday, November 18, 2014 01:58:11 PM Ken Xue wrote: > This new feature is to interpret AMD specific ACPI device to platform device > such as I2C, UART found on AMD CZ and later chipsets. It is based on example > INTEL LPSS. Now, it can support AMD I2C & UART. > > Signed-off-by: Ken Xue <Ken.Xue@amd.com> > Signed-off-by: Jeff Wu <Jeff.Wu@amd.com> Generally speaking, this seems to duplicate much code from acpi_lpss which should be re-used instead. What about moving the code that will be common between acpi_lpss and the new driver into a new file (say acpi_soc.c)? Also, you need to avoid automatic creation of platform devices when !X86_AMD_PLATFORM_DEVICE in analogy with what acpi_lpss does, or bad things will happen. > --- > arch/x86/Kconfig | 11 +++ > drivers/acpi/Makefile | 1 + > drivers/acpi/acpi_apd.c | 245 ++++++++++++++++++++++++++++++++++++++++++++++++ > drivers/acpi/internal.h | 6 ++ > drivers/acpi/scan.c | 1 + > 5 files changed, 264 insertions(+) > create mode 100644 drivers/acpi/acpi_apd.c > > diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig > index ded8a67..6402c79f 100644 > --- a/arch/x86/Kconfig > +++ b/arch/x86/Kconfig > @@ -495,6 +495,17 @@ config X86_INTEL_LPSS > things like clock tree (common clock framework) and pincontrol > which are needed by the LPSS peripheral drivers. > > +config X86_AMD_PLATFORM_DEVICE > + bool "AMD ACPI2Platform devices support" > + depends on ACPI > + select COMMON_CLK > + select PINCTRL > + ---help--- > + Select to interpret AMD specific ACPI device to platform device > + such as I2C, UART found on AMD CARRIZO and later chipset. Selecting > + this option enables things like clock tree (common clock framework) > + and pinctrl. > + > config IOSF_MBI > tristate "Intel SoC IOSF Sideband support for SoC platforms" > depends on PCI > diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile > index c3b2fcb..91fc1c2 100644 > --- a/drivers/acpi/Makefile > +++ b/drivers/acpi/Makefile > @@ -41,6 +41,7 @@ acpi-y += ec.o > acpi-$(CONFIG_ACPI_DOCK) += dock.o > acpi-y += pci_root.o pci_link.o pci_irq.o > acpi-y += acpi_lpss.o > +acpi-$(CONFIG_X86_AMD_PLATFORM_DEVICE) += acpi_apd.o > acpi-y += acpi_platform.o > acpi-y += acpi_pnp.o > acpi-y += int340x_thermal.o > diff --git a/drivers/acpi/acpi_apd.c b/drivers/acpi/acpi_apd.c > new file mode 100644 > index 0000000..994b7db > --- /dev/null > +++ b/drivers/acpi/acpi_apd.c > @@ -0,0 +1,245 @@ > +/* > + * AMD ACPI support for ACPI2platform device. > + * > + * Copyright (c) 2014, AMD Corporation. > + * Authors: Ken Xue <Ken.Xue@amd.com> > + * Jeff Wu <Jeff.Wu@amd.com> > + * > + * This program is free software; you can redistribute it and/or modify > + * it under the terms of the GNU General Public License version 2 as > + * published by the Free Software Foundation. > + */ > + > +#include <linux/acpi.h> > +#include <linux/clk.h> > +#include <linux/clkdev.h> > +#include <linux/clk-provider.h> > +#include <linux/err.h> > +#include <linux/io.h> > +#include <linux/platform_device.h> > +#include <linux/pm_runtime.h> > + > +#include "internal.h" > + > +ACPI_MODULE_NAME("acpi_apd"); > +struct apd_private_data; > + > +struct apd_device_desc { > + bool clk_required; > + bool fixed_root_clock; > + const char *clk_name; > + unsigned long rate; > + size_t prv_size_override; > + void (*setup)(struct apd_private_data *pdata); > +}; > + > +struct apd_private_data { > + void __iomem *mmio_base; > + resource_size_t mmio_size; > + struct clk *clk; > + const struct apd_device_desc *dev_desc; > +}; > + > +static struct apd_device_desc amd_i2c_desc = { > + .clk_required = true, > + .fixed_root_clock = true, > + .clk_name = "i2c_clk", > + .rate = 133000000, /*(133 * 1000 * 1000)*/ > +}; > + > +static struct apd_device_desc amd_uart_desc = { > + .clk_required = true, > + .fixed_root_clock = true, > + .clk_name = "uart_clk", > + .rate = 48000000, > +}; > + > +static const struct acpi_device_id acpi_apd_device_ids[] = { > + /* Generic apd devices */ > + { "AMD0010", (unsigned long)&amd_i2c_desc }, > + { "AMD0020", (unsigned long)&amd_uart_desc }, > + { } > +}; > + > +static int is_memory(struct acpi_resource *res, void *not_used) > +{ > + struct resource r; > + > + return !acpi_dev_resource_memory(res, &r); > +} > + > +static int register_device_clock(struct acpi_device *adev, > + struct apd_private_data *pdata) > +{ > + const struct apd_device_desc *dev_desc = pdata->dev_desc; > + struct clk *clk = ERR_PTR(-ENODEV); > + > + clk = pdata->clk; > + if (!clk && dev_desc->fixed_root_clock) { > + clk = clk_register_fixed_rate(&adev->dev, dev_name(&adev->dev), > + NULL, CLK_IS_ROOT, dev_desc->rate); > + pdata->clk = clk; > + clk_register_clkdev(clk, NULL, dev_name(&adev->dev)); > + } > + > + return 0; > +} > + > +static int acpi_apd_create_device(struct acpi_device *adev, > + const struct acpi_device_id *id) > +{ > + struct apd_device_desc *dev_desc; > + struct apd_private_data *pdata; > + struct resource_list_entry *rentry; > + struct list_head resource_list; > + struct platform_device *pdev; > + int ret; > + > + dev_desc = (struct apd_device_desc *)id->driver_data; > + if (!dev_desc) { > + pdev = acpi_create_platform_device(adev); > + return IS_ERR_OR_NULL(pdev) ? PTR_ERR(pdev) : 1; > + } > + > + pdata = kzalloc(sizeof(*pdata), GFP_KERNEL); > + if (!pdata) > + return -ENOMEM; > + > + INIT_LIST_HEAD(&resource_list); > + ret = acpi_dev_get_resources(adev, &resource_list, is_memory, NULL); > + if (ret < 0) > + goto err_out; > + > + list_for_each_entry(rentry, &resource_list, node) > + if (resource_type(&rentry->res) == IORESOURCE_MEM) { > + if (dev_desc->prv_size_override) > + pdata->mmio_size = dev_desc->prv_size_override; > + else > + pdata->mmio_size = resource_size(&rentry->res); > + pdata->mmio_base = ioremap(rentry->res.start, > + pdata->mmio_size); > + break; > + } > + > + acpi_dev_free_resource_list(&resource_list); > + > + pdata->dev_desc = dev_desc; > + > + if (dev_desc->clk_required) { > + ret = register_device_clock(adev, pdata); > + if (ret) { > + /* Skip the device, but continue the namespace scan. */ > + ret = 0; > + goto err_out; > + } > + } > + > + /* > + * This works around a known issue in ACPI tables where apd devices > + * have _PS0 and _PS3 without _PSC (and no power resources), so > + * acpi_bus_init_power() will assume that the BIOS has put them into D0. > + */ > + ret = acpi_device_fix_up_power(adev); > + if (ret) { > + /* Skip the device, but continue the namespace scan. */ > + ret = 0; > + goto err_out; > + } > + > + if (dev_desc->setup) > + dev_desc->setup(pdata); > + > + adev->driver_data = pdata; > + pdev = acpi_create_platform_device(adev); > + if (!IS_ERR_OR_NULL(pdev)) { > + device_enable_async_suspend(&pdev->dev); > + return ret; > + } > + > + ret = PTR_ERR(pdev); > + adev->driver_data = NULL; > + > + err_out: > + kfree(pdata); > + return ret; > +} > + > +static ssize_t apd_device_desc_show(struct device *dev, > + struct device_attribute *attr, char *buf) > +{ > + int ret; > + struct acpi_device *adev; > + struct apd_private_data *pdata; > + > + ret = acpi_bus_get_device(ACPI_HANDLE(dev), &adev); > + if (WARN_ON(ret)) > + return ret; > + > + pdata = acpi_driver_data(adev); > + if (WARN_ON(!pdata || !pdata->dev_desc)) > + return -ENODEV; > + > + if (pdata->dev_desc->clk_required) > + return sprintf(buf, "Required clk: %s %s %ld\n", > + pdata->dev_desc->clk_name, > + pdata->dev_desc->fixed_root_clock ? > + "fix rate" : "no fix rate", > + pdata->dev_desc->rate); > + else > + return sprintf(buf, "No need clk\n"); > +} > + > +static DEVICE_ATTR(device_desc, S_IRUSR, apd_device_desc_show, NULL); > + > +static struct attribute *apd_attrs[] = { > + &dev_attr_device_desc.attr, > + NULL, > +}; > + > +static struct attribute_group apd_attr_group = { > + .attrs = apd_attrs, > + .name = "apd_ltr", > +}; > + > +static int acpi_apd_platform_notify(struct notifier_block *nb, > + unsigned long action, void *data) > +{ > + struct platform_device *pdev = to_platform_device(data); > + struct apd_private_data *pdata; > + struct acpi_device *adev; > + const struct acpi_device_id *id; > + int ret = 0; > + > + id = acpi_match_device(acpi_apd_device_ids, &pdev->dev); > + if (!id || !id->driver_data) > + return 0; > + > + if (acpi_bus_get_device(ACPI_HANDLE(&pdev->dev), &adev)) > + return 0; > + > + pdata = acpi_driver_data(adev); > + if (!pdata || !pdata->mmio_base) > + return 0; > + > + if (action == BUS_NOTIFY_ADD_DEVICE) > + ret = sysfs_create_group(&pdev->dev.kobj, &apd_attr_group); > + else if (action == BUS_NOTIFY_DEL_DEVICE) > + sysfs_remove_group(&pdev->dev.kobj, &apd_attr_group); > + > + return ret; > +} > + > +static struct notifier_block acpi_apd_nb = { > + .notifier_call = acpi_apd_platform_notify, > +}; > + > +static struct acpi_scan_handler apd_handler = { > + .ids = acpi_apd_device_ids, > + .attach = acpi_apd_create_device, > +}; > + > +void __init acpi_apd_init(void) > +{ > + bus_register_notifier(&platform_bus_type, &acpi_apd_nb); > + acpi_scan_add_handler(&apd_handler); > +} > diff --git a/drivers/acpi/internal.h b/drivers/acpi/internal.h > index 447f6d6..c8a0e8e 100644 > --- a/drivers/acpi/internal.h > +++ b/drivers/acpi/internal.h > @@ -68,6 +68,12 @@ static inline void acpi_debugfs_init(void) { return; } > #endif > void acpi_lpss_init(void); > > +#ifdef CONFIG_X86_AMD_PLATFORM_DEVICE > +void acpi_apd_init(void); > +#else > +static inline void acpi_apd_init(void) {} > +#endif > + > acpi_status acpi_hotplug_schedule(struct acpi_device *adev, u32 src); > bool acpi_queue_hotplug_work(struct work_struct *work); > void acpi_device_hotplug(struct acpi_device *adev, u32 src); > diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c > index 0476e90..24fef2b 100644 > --- a/drivers/acpi/scan.c > +++ b/drivers/acpi/scan.c > @@ -2349,6 +2349,7 @@ int __init acpi_scan_init(void) > acpi_pci_link_init(); > acpi_processor_init(); > acpi_lpss_init(); > + acpi_apd_init(); > acpi_cmos_rtc_init(); > acpi_container_init(); > acpi_memory_hotplug_init(); >
On Monday, November 24, 2014 01:02:30 AM Xue, Ken wrote: > > On Tuesday, November 18, 2014 01:58:11 PM Ken Xue wrote: > > This new feature is to interpret AMD specific ACPI device to platform > > device such as I2C, UART found on AMD CZ and later chipsets. It is > > based on example INTEL LPSS. Now, it can support AMD I2C & UART. > > > > Signed-off-by: Ken Xue <Ken.Xue@amd.com> > > Signed-off-by: Jeff Wu <Jeff.Wu@amd.com> > > Generally speaking, this seems to duplicate much code from acpi_lpss which should be re-used instead. What about moving the code that will be common between acpi_lpss and the new driver into a new file (say acpi_soc.c)? > > Also, you need to avoid automatic creation of platform devices when !X86_AMD_PLATFORM_DEVICE in analogy with what acpi_lpss does, or bad things will happen. > > [ken] sounds fair enough. Let me take action to merge drivers to acpi_soc.c ? or you have other plan? I'd prefer the common code to reside in one file (or one .c file and one header file), and the driver-specific code to stay in separate per-driver files.
diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig index ded8a67..6402c79f 100644 --- a/arch/x86/Kconfig +++ b/arch/x86/Kconfig @@ -495,6 +495,17 @@ config X86_INTEL_LPSS things like clock tree (common clock framework) and pincontrol which are needed by the LPSS peripheral drivers. +config X86_AMD_PLATFORM_DEVICE + bool "AMD ACPI2Platform devices support" + depends on ACPI + select COMMON_CLK + select PINCTRL + ---help--- + Select to interpret AMD specific ACPI device to platform device + such as I2C, UART found on AMD CARRIZO and later chipset. Selecting + this option enables things like clock tree (common clock framework) + and pinctrl. + config IOSF_MBI tristate "Intel SoC IOSF Sideband support for SoC platforms" depends on PCI diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile index c3b2fcb..91fc1c2 100644 --- a/drivers/acpi/Makefile +++ b/drivers/acpi/Makefile @@ -41,6 +41,7 @@ acpi-y += ec.o acpi-$(CONFIG_ACPI_DOCK) += dock.o acpi-y += pci_root.o pci_link.o pci_irq.o acpi-y += acpi_lpss.o +acpi-$(CONFIG_X86_AMD_PLATFORM_DEVICE) += acpi_apd.o acpi-y += acpi_platform.o acpi-y += acpi_pnp.o acpi-y += int340x_thermal.o diff --git a/drivers/acpi/acpi_apd.c b/drivers/acpi/acpi_apd.c new file mode 100644 index 0000000..994b7db --- /dev/null +++ b/drivers/acpi/acpi_apd.c @@ -0,0 +1,245 @@ +/* + * AMD ACPI support for ACPI2platform device. + * + * Copyright (c) 2014, AMD Corporation. + * Authors: Ken Xue <Ken.Xue@amd.com> + * Jeff Wu <Jeff.Wu@amd.com> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + */ + +#include <linux/acpi.h> +#include <linux/clk.h> +#include <linux/clkdev.h> +#include <linux/clk-provider.h> +#include <linux/err.h> +#include <linux/io.h> +#include <linux/platform_device.h> +#include <linux/pm_runtime.h> + +#include "internal.h" + +ACPI_MODULE_NAME("acpi_apd"); +struct apd_private_data; + +struct apd_device_desc { + bool clk_required; + bool fixed_root_clock; + const char *clk_name; + unsigned long rate; + size_t prv_size_override; + void (*setup)(struct apd_private_data *pdata); +}; + +struct apd_private_data { + void __iomem *mmio_base; + resource_size_t mmio_size; + struct clk *clk; + const struct apd_device_desc *dev_desc; +}; + +static struct apd_device_desc amd_i2c_desc = { + .clk_required = true, + .fixed_root_clock = true, + .clk_name = "i2c_clk", + .rate = 133000000, /*(133 * 1000 * 1000)*/ +}; + +static struct apd_device_desc amd_uart_desc = { + .clk_required = true, + .fixed_root_clock = true, + .clk_name = "uart_clk", + .rate = 48000000, +}; + +static const struct acpi_device_id acpi_apd_device_ids[] = { + /* Generic apd devices */ + { "AMD0010", (unsigned long)&amd_i2c_desc }, + { "AMD0020", (unsigned long)&amd_uart_desc }, + { } +}; + +static int is_memory(struct acpi_resource *res, void *not_used) +{ + struct resource r; + + return !acpi_dev_resource_memory(res, &r); +} + +static int register_device_clock(struct acpi_device *adev, + struct apd_private_data *pdata) +{ + const struct apd_device_desc *dev_desc = pdata->dev_desc; + struct clk *clk = ERR_PTR(-ENODEV); + + clk = pdata->clk; + if (!clk && dev_desc->fixed_root_clock) { + clk = clk_register_fixed_rate(&adev->dev, dev_name(&adev->dev), + NULL, CLK_IS_ROOT, dev_desc->rate); + pdata->clk = clk; + clk_register_clkdev(clk, NULL, dev_name(&adev->dev)); + } + + return 0; +} + +static int acpi_apd_create_device(struct acpi_device *adev, + const struct acpi_device_id *id) +{ + struct apd_device_desc *dev_desc; + struct apd_private_data *pdata; + struct resource_list_entry *rentry; + struct list_head resource_list; + struct platform_device *pdev; + int ret; + + dev_desc = (struct apd_device_desc *)id->driver_data; + if (!dev_desc) { + pdev = acpi_create_platform_device(adev); + return IS_ERR_OR_NULL(pdev) ? PTR_ERR(pdev) : 1; + } + + pdata = kzalloc(sizeof(*pdata), GFP_KERNEL); + if (!pdata) + return -ENOMEM; + + INIT_LIST_HEAD(&resource_list); + ret = acpi_dev_get_resources(adev, &resource_list, is_memory, NULL); + if (ret < 0) + goto err_out; + + list_for_each_entry(rentry, &resource_list, node) + if (resource_type(&rentry->res) == IORESOURCE_MEM) { + if (dev_desc->prv_size_override) + pdata->mmio_size = dev_desc->prv_size_override; + else + pdata->mmio_size = resource_size(&rentry->res); + pdata->mmio_base = ioremap(rentry->res.start, + pdata->mmio_size); + break; + } + + acpi_dev_free_resource_list(&resource_list); + + pdata->dev_desc = dev_desc; + + if (dev_desc->clk_required) { + ret = register_device_clock(adev, pdata); + if (ret) { + /* Skip the device, but continue the namespace scan. */ + ret = 0; + goto err_out; + } + } + + /* + * This works around a known issue in ACPI tables where apd devices + * have _PS0 and _PS3 without _PSC (and no power resources), so + * acpi_bus_init_power() will assume that the BIOS has put them into D0. + */ + ret = acpi_device_fix_up_power(adev); + if (ret) { + /* Skip the device, but continue the namespace scan. */ + ret = 0; + goto err_out; + } + + if (dev_desc->setup) + dev_desc->setup(pdata); + + adev->driver_data = pdata; + pdev = acpi_create_platform_device(adev); + if (!IS_ERR_OR_NULL(pdev)) { + device_enable_async_suspend(&pdev->dev); + return ret; + } + + ret = PTR_ERR(pdev); + adev->driver_data = NULL; + + err_out: + kfree(pdata); + return ret; +} + +static ssize_t apd_device_desc_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + int ret; + struct acpi_device *adev; + struct apd_private_data *pdata; + + ret = acpi_bus_get_device(ACPI_HANDLE(dev), &adev); + if (WARN_ON(ret)) + return ret; + + pdata = acpi_driver_data(adev); + if (WARN_ON(!pdata || !pdata->dev_desc)) + return -ENODEV; + + if (pdata->dev_desc->clk_required) + return sprintf(buf, "Required clk: %s %s %ld\n", + pdata->dev_desc->clk_name, + pdata->dev_desc->fixed_root_clock ? + "fix rate" : "no fix rate", + pdata->dev_desc->rate); + else + return sprintf(buf, "No need clk\n"); +} + +static DEVICE_ATTR(device_desc, S_IRUSR, apd_device_desc_show, NULL); + +static struct attribute *apd_attrs[] = { + &dev_attr_device_desc.attr, + NULL, +}; + +static struct attribute_group apd_attr_group = { + .attrs = apd_attrs, + .name = "apd_ltr", +}; + +static int acpi_apd_platform_notify(struct notifier_block *nb, + unsigned long action, void *data) +{ + struct platform_device *pdev = to_platform_device(data); + struct apd_private_data *pdata; + struct acpi_device *adev; + const struct acpi_device_id *id; + int ret = 0; + + id = acpi_match_device(acpi_apd_device_ids, &pdev->dev); + if (!id || !id->driver_data) + return 0; + + if (acpi_bus_get_device(ACPI_HANDLE(&pdev->dev), &adev)) + return 0; + + pdata = acpi_driver_data(adev); + if (!pdata || !pdata->mmio_base) + return 0; + + if (action == BUS_NOTIFY_ADD_DEVICE) + ret = sysfs_create_group(&pdev->dev.kobj, &apd_attr_group); + else if (action == BUS_NOTIFY_DEL_DEVICE) + sysfs_remove_group(&pdev->dev.kobj, &apd_attr_group); + + return ret; +} + +static struct notifier_block acpi_apd_nb = { + .notifier_call = acpi_apd_platform_notify, +}; + +static struct acpi_scan_handler apd_handler = { + .ids = acpi_apd_device_ids, + .attach = acpi_apd_create_device, +}; + +void __init acpi_apd_init(void) +{ + bus_register_notifier(&platform_bus_type, &acpi_apd_nb); + acpi_scan_add_handler(&apd_handler); +} diff --git a/drivers/acpi/internal.h b/drivers/acpi/internal.h index 447f6d6..c8a0e8e 100644 --- a/drivers/acpi/internal.h +++ b/drivers/acpi/internal.h @@ -68,6 +68,12 @@ static inline void acpi_debugfs_init(void) { return; } #endif void acpi_lpss_init(void); +#ifdef CONFIG_X86_AMD_PLATFORM_DEVICE +void acpi_apd_init(void); +#else +static inline void acpi_apd_init(void) {} +#endif + acpi_status acpi_hotplug_schedule(struct acpi_device *adev, u32 src); bool acpi_queue_hotplug_work(struct work_struct *work); void acpi_device_hotplug(struct acpi_device *adev, u32 src); diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 0476e90..24fef2b 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -2349,6 +2349,7 @@ int __init acpi_scan_init(void) acpi_pci_link_init(); acpi_processor_init(); acpi_lpss_init(); + acpi_apd_init(); acpi_cmos_rtc_init(); acpi_container_init(); acpi_memory_hotplug_init();