diff options
-rw-r--r-- | drivers/acpi/Makefile | 1 | ||||
-rw-r--r-- | drivers/acpi/acpi_amba.c | 122 | ||||
-rw-r--r-- | drivers/acpi/acpi_platform.c | 19 | ||||
-rw-r--r-- | drivers/acpi/apei/apei-base.c | 6 | ||||
-rw-r--r-- | drivers/acpi/apei/erst.c | 3 | ||||
-rw-r--r-- | drivers/acpi/bus.c | 26 | ||||
-rw-r--r-- | drivers/acpi/internal.h | 7 | ||||
-rw-r--r-- | drivers/acpi/osl.c | 158 | ||||
-rw-r--r-- | drivers/acpi/scan.c | 1 | ||||
-rw-r--r-- | drivers/acpi/tables.c | 2 |
10 files changed, 260 insertions, 85 deletions
diff --git a/drivers/acpi/Makefile b/drivers/acpi/Makefile index cb648a49543a..edeb2d1d99be 100644 --- a/drivers/acpi/Makefile +++ b/drivers/acpi/Makefile | |||
@@ -43,6 +43,7 @@ acpi-y += pci_root.o pci_link.o pci_irq.o | |||
43 | acpi-y += acpi_lpss.o acpi_apd.o | 43 | acpi-y += acpi_lpss.o acpi_apd.o |
44 | acpi-y += acpi_platform.o | 44 | acpi-y += acpi_platform.o |
45 | acpi-y += acpi_pnp.o | 45 | acpi-y += acpi_pnp.o |
46 | acpi-$(CONFIG_ARM_AMBA) += acpi_amba.o | ||
46 | acpi-y += int340x_thermal.o | 47 | acpi-y += int340x_thermal.o |
47 | acpi-y += power.o | 48 | acpi-y += power.o |
48 | acpi-y += event.o | 49 | acpi-y += event.o |
diff --git a/drivers/acpi/acpi_amba.c b/drivers/acpi/acpi_amba.c new file mode 100644 index 000000000000..2a61b54ab968 --- /dev/null +++ b/drivers/acpi/acpi_amba.c | |||
@@ -0,0 +1,122 @@ | |||
1 | |||
2 | /* | ||
3 | * ACPI support for platform bus type. | ||
4 | * | ||
5 | * Copyright (C) 2015, Linaro Ltd | ||
6 | * Author: Graeme Gregory <graeme.gregory@linaro.org> | ||
7 | * | ||
8 | * This program is free software; you can redistribute it and/or modify | ||
9 | * it under the terms of the GNU General Public License version 2 as | ||
10 | * published by the Free Software Foundation. | ||
11 | */ | ||
12 | |||
13 | #include <linux/acpi.h> | ||
14 | #include <linux/amba/bus.h> | ||
15 | #include <linux/clkdev.h> | ||
16 | #include <linux/clk-provider.h> | ||
17 | #include <linux/device.h> | ||
18 | #include <linux/err.h> | ||
19 | #include <linux/ioport.h> | ||
20 | #include <linux/kernel.h> | ||
21 | #include <linux/module.h> | ||
22 | |||
23 | #include "internal.h" | ||
24 | |||
25 | static const struct acpi_device_id amba_id_list[] = { | ||
26 | {"ARMH0061", 0}, /* PL061 GPIO Device */ | ||
27 | {"", 0}, | ||
28 | }; | ||
29 | |||
30 | static void amba_register_dummy_clk(void) | ||
31 | { | ||
32 | static struct clk *amba_dummy_clk; | ||
33 | |||
34 | /* If clock already registered */ | ||
35 | if (amba_dummy_clk) | ||
36 | return; | ||
37 | |||
38 | amba_dummy_clk = clk_register_fixed_rate(NULL, "apb_pclk", NULL, | ||
39 | CLK_IS_ROOT, 0); | ||
40 | clk_register_clkdev(amba_dummy_clk, "apb_pclk", NULL); | ||
41 | } | ||
42 | |||
43 | static int amba_handler_attach(struct acpi_device *adev, | ||
44 | const struct acpi_device_id *id) | ||
45 | { | ||
46 | struct amba_device *dev; | ||
47 | struct resource_entry *rentry; | ||
48 | struct list_head resource_list; | ||
49 | bool address_found = false; | ||
50 | int irq_no = 0; | ||
51 | int ret; | ||
52 | |||
53 | /* If the ACPI node already has a physical device attached, skip it. */ | ||
54 | if (adev->physical_node_count) | ||
55 | return 0; | ||
56 | |||
57 | dev = amba_device_alloc(dev_name(&adev->dev), 0, 0); | ||
58 | if (!dev) { | ||
59 | dev_err(&adev->dev, "%s(): amba_device_alloc() failed\n", | ||
60 | __func__); | ||
61 | return -ENOMEM; | ||
62 | } | ||
63 | |||
64 | INIT_LIST_HEAD(&resource_list); | ||
65 | ret = acpi_dev_get_resources(adev, &resource_list, NULL, NULL); | ||
66 | if (ret < 0) | ||
67 | goto err_free; | ||
68 | |||
69 | list_for_each_entry(rentry, &resource_list, node) { | ||
70 | switch (resource_type(rentry->res)) { | ||
71 | case IORESOURCE_MEM: | ||
72 | if (!address_found) { | ||
73 | dev->res = *rentry->res; | ||
74 | address_found = true; | ||
75 | } | ||
76 | break; | ||
77 | case IORESOURCE_IRQ: | ||
78 | if (irq_no < AMBA_NR_IRQS) | ||
79 | dev->irq[irq_no++] = rentry->res->start; | ||
80 | break; | ||
81 | default: | ||
82 | dev_warn(&adev->dev, "Invalid resource\n"); | ||
83 | break; | ||
84 | } | ||
85 | } | ||
86 | |||
87 | acpi_dev_free_resource_list(&resource_list); | ||
88 | |||
89 | /* | ||
90 | * If the ACPI node has a parent and that parent has a physical device | ||
91 | * attached to it, that physical device should be the parent of | ||
92 | * the amba device we are about to create. | ||
93 | */ | ||
94 | if (adev->parent) | ||
95 | dev->dev.parent = acpi_get_first_physical_node(adev->parent); | ||
96 | |||
97 | ACPI_COMPANION_SET(&dev->dev, adev); | ||
98 | |||
99 | ret = amba_device_add(dev, &iomem_resource); | ||
100 | if (ret) { | ||
101 | dev_err(&adev->dev, "%s(): amba_device_add() failed (%d)\n", | ||
102 | __func__, ret); | ||
103 | goto err_free; | ||
104 | } | ||
105 | |||
106 | return 1; | ||
107 | |||
108 | err_free: | ||
109 | amba_device_put(dev); | ||
110 | return ret; | ||
111 | } | ||
112 | |||
113 | static struct acpi_scan_handler amba_handler = { | ||
114 | .ids = amba_id_list, | ||
115 | .attach = amba_handler_attach, | ||
116 | }; | ||
117 | |||
118 | void __init acpi_amba_init(void) | ||
119 | { | ||
120 | amba_register_dummy_clk(); | ||
121 | acpi_scan_add_handler(&amba_handler); | ||
122 | } | ||
diff --git a/drivers/acpi/acpi_platform.c b/drivers/acpi/acpi_platform.c index 296b7a14893a..c3af1088bf6b 100644 --- a/drivers/acpi/acpi_platform.c +++ b/drivers/acpi/acpi_platform.c | |||
@@ -43,7 +43,6 @@ static const struct acpi_device_id forbidden_id_list[] = { | |||
43 | struct platform_device *acpi_create_platform_device(struct acpi_device *adev) | 43 | struct platform_device *acpi_create_platform_device(struct acpi_device *adev) |
44 | { | 44 | { |
45 | struct platform_device *pdev = NULL; | 45 | struct platform_device *pdev = NULL; |
46 | struct acpi_device *acpi_parent; | ||
47 | struct platform_device_info pdevinfo; | 46 | struct platform_device_info pdevinfo; |
48 | struct resource_entry *rentry; | 47 | struct resource_entry *rentry; |
49 | struct list_head resource_list; | 48 | struct list_head resource_list; |
@@ -82,22 +81,8 @@ struct platform_device *acpi_create_platform_device(struct acpi_device *adev) | |||
82 | * attached to it, that physical device should be the parent of the | 81 | * attached to it, that physical device should be the parent of the |
83 | * platform device we are about to create. | 82 | * platform device we are about to create. |
84 | */ | 83 | */ |
85 | pdevinfo.parent = NULL; | 84 | pdevinfo.parent = adev->parent ? |
86 | acpi_parent = adev->parent; | 85 | acpi_get_first_physical_node(adev->parent) : NULL; |
87 | if (acpi_parent) { | ||
88 | struct acpi_device_physical_node *entry; | ||
89 | struct list_head *list; | ||
90 | |||
91 | mutex_lock(&acpi_parent->physical_node_lock); | ||
92 | list = &acpi_parent->physical_node_list; | ||
93 | if (!list_empty(list)) { | ||
94 | entry = list_first_entry(list, | ||
95 | struct acpi_device_physical_node, | ||
96 | node); | ||
97 | pdevinfo.parent = entry->dev; | ||
98 | } | ||
99 | mutex_unlock(&acpi_parent->physical_node_lock); | ||
100 | } | ||
101 | pdevinfo.name = dev_name(&adev->dev); | 86 | pdevinfo.name = dev_name(&adev->dev); |
102 | pdevinfo.id = -1; | 87 | pdevinfo.id = -1; |
103 | pdevinfo.res = resources; | 88 | pdevinfo.res = resources; |
diff --git a/drivers/acpi/apei/apei-base.c b/drivers/acpi/apei/apei-base.c index a2c8d7adb6eb..da370e1d31f4 100644 --- a/drivers/acpi/apei/apei-base.c +++ b/drivers/acpi/apei/apei-base.c | |||
@@ -536,7 +536,8 @@ int apei_resources_request(struct apei_resources *resources, | |||
536 | goto err_unmap_ioport; | 536 | goto err_unmap_ioport; |
537 | } | 537 | } |
538 | 538 | ||
539 | return 0; | 539 | goto arch_res_fini; |
540 | |||
540 | err_unmap_ioport: | 541 | err_unmap_ioport: |
541 | list_for_each_entry(res, &resources->ioport, list) { | 542 | list_for_each_entry(res, &resources->ioport, list) { |
542 | if (res == res_bak) | 543 | if (res == res_bak) |
@@ -551,7 +552,8 @@ err_unmap_iomem: | |||
551 | release_mem_region(res->start, res->end - res->start); | 552 | release_mem_region(res->start, res->end - res->start); |
552 | } | 553 | } |
553 | arch_res_fini: | 554 | arch_res_fini: |
554 | apei_resources_fini(&arch_res); | 555 | if (arch_apei_filter_addr) |
556 | apei_resources_fini(&arch_res); | ||
555 | nvs_res_fini: | 557 | nvs_res_fini: |
556 | apei_resources_fini(&nvs_resources); | 558 | apei_resources_fini(&nvs_resources); |
557 | return rc; | 559 | return rc; |
diff --git a/drivers/acpi/apei/erst.c b/drivers/acpi/apei/erst.c index 6e6bc1059301..006c3894c6ea 100644 --- a/drivers/acpi/apei/erst.c +++ b/drivers/acpi/apei/erst.c | |||
@@ -1207,6 +1207,9 @@ static int __init erst_init(void) | |||
1207 | "Failed to allocate %lld bytes for persistent store error log.\n", | 1207 | "Failed to allocate %lld bytes for persistent store error log.\n", |
1208 | erst_erange.size); | 1208 | erst_erange.size); |
1209 | 1209 | ||
1210 | /* Cleanup ERST Resources */ | ||
1211 | apei_resources_fini(&erst_resources); | ||
1212 | |||
1210 | return 0; | 1213 | return 0; |
1211 | 1214 | ||
1212 | err_release_erange: | 1215 | err_release_erange: |
diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c index 891c42d1cd65..0e8567846f1a 100644 --- a/drivers/acpi/bus.c +++ b/drivers/acpi/bus.c | |||
@@ -479,24 +479,38 @@ static void acpi_device_remove_notify_handler(struct acpi_device *device) | |||
479 | Device Matching | 479 | Device Matching |
480 | -------------------------------------------------------------------------- */ | 480 | -------------------------------------------------------------------------- */ |
481 | 481 | ||
482 | static struct acpi_device *acpi_primary_dev_companion(struct acpi_device *adev, | 482 | /** |
483 | const struct device *dev) | 483 | * acpi_get_first_physical_node - Get first physical node of an ACPI device |
484 | * @adev: ACPI device in question | ||
485 | * | ||
486 | * Return: First physical node of ACPI device @adev | ||
487 | */ | ||
488 | struct device *acpi_get_first_physical_node(struct acpi_device *adev) | ||
484 | { | 489 | { |
485 | struct mutex *physical_node_lock = &adev->physical_node_lock; | 490 | struct mutex *physical_node_lock = &adev->physical_node_lock; |
491 | struct device *phys_dev; | ||
486 | 492 | ||
487 | mutex_lock(physical_node_lock); | 493 | mutex_lock(physical_node_lock); |
488 | if (list_empty(&adev->physical_node_list)) { | 494 | if (list_empty(&adev->physical_node_list)) { |
489 | adev = NULL; | 495 | phys_dev = NULL; |
490 | } else { | 496 | } else { |
491 | const struct acpi_device_physical_node *node; | 497 | const struct acpi_device_physical_node *node; |
492 | 498 | ||
493 | node = list_first_entry(&adev->physical_node_list, | 499 | node = list_first_entry(&adev->physical_node_list, |
494 | struct acpi_device_physical_node, node); | 500 | struct acpi_device_physical_node, node); |
495 | if (node->dev != dev) | 501 | |
496 | adev = NULL; | 502 | phys_dev = node->dev; |
497 | } | 503 | } |
498 | mutex_unlock(physical_node_lock); | 504 | mutex_unlock(physical_node_lock); |
499 | return adev; | 505 | return phys_dev; |
506 | } | ||
507 | |||
508 | static struct acpi_device *acpi_primary_dev_companion(struct acpi_device *adev, | ||
509 | const struct device *dev) | ||
510 | { | ||
511 | const struct device *phys_dev = acpi_get_first_physical_node(adev); | ||
512 | |||
513 | return phys_dev && phys_dev == dev ? adev : NULL; | ||
500 | } | 514 | } |
501 | 515 | ||
502 | /** | 516 | /** |
diff --git a/drivers/acpi/internal.h b/drivers/acpi/internal.h index 1e6833a5cd44..a37508ef66c1 100644 --- a/drivers/acpi/internal.h +++ b/drivers/acpi/internal.h | |||
@@ -20,6 +20,7 @@ | |||
20 | 20 | ||
21 | #define PREFIX "ACPI: " | 21 | #define PREFIX "ACPI: " |
22 | 22 | ||
23 | void acpi_initrd_initialize_tables(void); | ||
23 | acpi_status acpi_os_initialize1(void); | 24 | acpi_status acpi_os_initialize1(void); |
24 | void init_acpi_device_notify(void); | 25 | void init_acpi_device_notify(void); |
25 | int acpi_scan_init(void); | 26 | int acpi_scan_init(void); |
@@ -29,6 +30,11 @@ void acpi_processor_init(void); | |||
29 | void acpi_platform_init(void); | 30 | void acpi_platform_init(void); |
30 | void acpi_pnp_init(void); | 31 | void acpi_pnp_init(void); |
31 | void acpi_int340x_thermal_init(void); | 32 | void acpi_int340x_thermal_init(void); |
33 | #ifdef CONFIG_ARM_AMBA | ||
34 | void acpi_amba_init(void); | ||
35 | #else | ||
36 | static inline void acpi_amba_init(void) {} | ||
37 | #endif | ||
32 | int acpi_sysfs_init(void); | 38 | int acpi_sysfs_init(void); |
33 | void acpi_container_init(void); | 39 | void acpi_container_init(void); |
34 | void acpi_memory_hotplug_init(void); | 40 | void acpi_memory_hotplug_init(void); |
@@ -106,6 +112,7 @@ bool acpi_device_is_present(struct acpi_device *adev); | |||
106 | bool acpi_device_is_battery(struct acpi_device *adev); | 112 | bool acpi_device_is_battery(struct acpi_device *adev); |
107 | bool acpi_device_is_first_physical_node(struct acpi_device *adev, | 113 | bool acpi_device_is_first_physical_node(struct acpi_device *adev, |
108 | const struct device *dev); | 114 | const struct device *dev); |
115 | struct device *acpi_get_first_physical_node(struct acpi_device *adev); | ||
109 | 116 | ||
110 | /* -------------------------------------------------------------------------- | 117 | /* -------------------------------------------------------------------------- |
111 | Device Matching and Notification | 118 | Device Matching and Notification |
diff --git a/drivers/acpi/osl.c b/drivers/acpi/osl.c index 67da6fb72274..814d5f83b75e 100644 --- a/drivers/acpi/osl.c +++ b/drivers/acpi/osl.c | |||
@@ -602,6 +602,14 @@ acpi_os_predefined_override(const struct acpi_predefined_names *init_val, | |||
602 | return AE_OK; | 602 | return AE_OK; |
603 | } | 603 | } |
604 | 604 | ||
605 | static void acpi_table_taint(struct acpi_table_header *table) | ||
606 | { | ||
607 | pr_warn(PREFIX | ||
608 | "Override [%4.4s-%8.8s], this is unsafe: tainting kernel\n", | ||
609 | table->signature, table->oem_table_id); | ||
610 | add_taint(TAINT_OVERRIDDEN_ACPI_TABLE, LOCKDEP_NOW_UNRELIABLE); | ||
611 | } | ||
612 | |||
605 | #ifdef CONFIG_ACPI_INITRD_TABLE_OVERRIDE | 613 | #ifdef CONFIG_ACPI_INITRD_TABLE_OVERRIDE |
606 | #include <linux/earlycpio.h> | 614 | #include <linux/earlycpio.h> |
607 | #include <linux/memblock.h> | 615 | #include <linux/memblock.h> |
@@ -636,6 +644,7 @@ static const char * const table_sigs[] = { | |||
636 | 644 | ||
637 | #define ACPI_OVERRIDE_TABLES 64 | 645 | #define ACPI_OVERRIDE_TABLES 64 |
638 | static struct cpio_data __initdata acpi_initrd_files[ACPI_OVERRIDE_TABLES]; | 646 | static struct cpio_data __initdata acpi_initrd_files[ACPI_OVERRIDE_TABLES]; |
647 | static DECLARE_BITMAP(acpi_initrd_installed, ACPI_OVERRIDE_TABLES); | ||
639 | 648 | ||
640 | #define MAP_CHUNK_SIZE (NR_FIX_BTMAPS << PAGE_SHIFT) | 649 | #define MAP_CHUNK_SIZE (NR_FIX_BTMAPS << PAGE_SHIFT) |
641 | 650 | ||
@@ -746,96 +755,125 @@ void __init acpi_initrd_override(void *data, size_t size) | |||
746 | } | 755 | } |
747 | } | 756 | } |
748 | } | 757 | } |
749 | #endif /* CONFIG_ACPI_INITRD_TABLE_OVERRIDE */ | ||
750 | 758 | ||
751 | static void acpi_table_taint(struct acpi_table_header *table) | 759 | acpi_status |
760 | acpi_os_physical_table_override(struct acpi_table_header *existing_table, | ||
761 | acpi_physical_address *address, u32 *length) | ||
752 | { | 762 | { |
753 | pr_warn(PREFIX | 763 | int table_offset = 0; |
754 | "Override [%4.4s-%8.8s], this is unsafe: tainting kernel\n", | 764 | int table_index = 0; |
755 | table->signature, table->oem_table_id); | 765 | struct acpi_table_header *table; |
756 | add_taint(TAINT_OVERRIDDEN_ACPI_TABLE, LOCKDEP_NOW_UNRELIABLE); | 766 | u32 table_length; |
757 | } | ||
758 | 767 | ||
768 | *length = 0; | ||
769 | *address = 0; | ||
770 | if (!acpi_tables_addr) | ||
771 | return AE_OK; | ||
759 | 772 | ||
760 | acpi_status | 773 | while (table_offset + ACPI_HEADER_SIZE <= all_tables_size) { |
761 | acpi_os_table_override(struct acpi_table_header * existing_table, | 774 | table = acpi_os_map_memory(acpi_tables_addr + table_offset, |
762 | struct acpi_table_header ** new_table) | 775 | ACPI_HEADER_SIZE); |
763 | { | 776 | if (table_offset + table->length > all_tables_size) { |
764 | if (!existing_table || !new_table) | 777 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); |
765 | return AE_BAD_PARAMETER; | 778 | WARN_ON(1); |
779 | return AE_OK; | ||
780 | } | ||
766 | 781 | ||
767 | *new_table = NULL; | 782 | table_length = table->length; |
768 | 783 | ||
769 | #ifdef CONFIG_ACPI_CUSTOM_DSDT | 784 | /* Only override tables matched */ |
770 | if (strncmp(existing_table->signature, "DSDT", 4) == 0) | 785 | if (test_bit(table_index, acpi_initrd_installed) || |
771 | *new_table = (struct acpi_table_header *)AmlCode; | 786 | memcmp(existing_table->signature, table->signature, 4) || |
772 | #endif | 787 | memcmp(table->oem_table_id, existing_table->oem_table_id, |
773 | if (*new_table != NULL) | 788 | ACPI_OEM_TABLE_ID_SIZE)) { |
789 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); | ||
790 | goto next_table; | ||
791 | } | ||
792 | |||
793 | *length = table_length; | ||
794 | *address = acpi_tables_addr + table_offset; | ||
774 | acpi_table_taint(existing_table); | 795 | acpi_table_taint(existing_table); |
796 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); | ||
797 | set_bit(table_index, acpi_initrd_installed); | ||
798 | break; | ||
799 | |||
800 | next_table: | ||
801 | table_offset += table_length; | ||
802 | table_index++; | ||
803 | } | ||
775 | return AE_OK; | 804 | return AE_OK; |
776 | } | 805 | } |
777 | 806 | ||
778 | acpi_status | 807 | void __init acpi_initrd_initialize_tables(void) |
779 | acpi_os_physical_table_override(struct acpi_table_header *existing_table, | ||
780 | acpi_physical_address *address, | ||
781 | u32 *table_length) | ||
782 | { | 808 | { |
783 | #ifndef CONFIG_ACPI_INITRD_TABLE_OVERRIDE | ||
784 | *table_length = 0; | ||
785 | *address = 0; | ||
786 | return AE_OK; | ||
787 | #else | ||
788 | int table_offset = 0; | 809 | int table_offset = 0; |
810 | int table_index = 0; | ||
811 | u32 table_length; | ||
789 | struct acpi_table_header *table; | 812 | struct acpi_table_header *table; |
790 | 813 | ||
791 | *table_length = 0; | ||
792 | *address = 0; | ||
793 | |||
794 | if (!acpi_tables_addr) | 814 | if (!acpi_tables_addr) |
795 | return AE_OK; | 815 | return; |
796 | |||
797 | do { | ||
798 | if (table_offset + ACPI_HEADER_SIZE > all_tables_size) { | ||
799 | WARN_ON(1); | ||
800 | return AE_OK; | ||
801 | } | ||
802 | 816 | ||
817 | while (table_offset + ACPI_HEADER_SIZE <= all_tables_size) { | ||
803 | table = acpi_os_map_memory(acpi_tables_addr + table_offset, | 818 | table = acpi_os_map_memory(acpi_tables_addr + table_offset, |
804 | ACPI_HEADER_SIZE); | 819 | ACPI_HEADER_SIZE); |
805 | |||
806 | if (table_offset + table->length > all_tables_size) { | 820 | if (table_offset + table->length > all_tables_size) { |
807 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); | 821 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); |
808 | WARN_ON(1); | 822 | WARN_ON(1); |
809 | return AE_OK; | 823 | return; |
810 | } | 824 | } |
811 | 825 | ||
812 | table_offset += table->length; | 826 | table_length = table->length; |
813 | 827 | ||
814 | if (memcmp(existing_table->signature, table->signature, 4)) { | 828 | /* Skip RSDT/XSDT which should only be used for override */ |
815 | acpi_os_unmap_memory(table, | 829 | if (test_bit(table_index, acpi_initrd_installed) || |
816 | ACPI_HEADER_SIZE); | 830 | ACPI_COMPARE_NAME(table->signature, ACPI_SIG_RSDT) || |
817 | continue; | 831 | ACPI_COMPARE_NAME(table->signature, ACPI_SIG_XSDT)) { |
818 | } | 832 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); |
819 | 833 | goto next_table; | |
820 | /* Only override tables with matching oem id */ | ||
821 | if (memcmp(table->oem_table_id, existing_table->oem_table_id, | ||
822 | ACPI_OEM_TABLE_ID_SIZE)) { | ||
823 | acpi_os_unmap_memory(table, | ||
824 | ACPI_HEADER_SIZE); | ||
825 | continue; | ||
826 | } | 834 | } |
827 | 835 | ||
828 | table_offset -= table->length; | 836 | acpi_table_taint(table); |
829 | *table_length = table->length; | ||
830 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); | 837 | acpi_os_unmap_memory(table, ACPI_HEADER_SIZE); |
831 | *address = acpi_tables_addr + table_offset; | 838 | acpi_install_table(acpi_tables_addr + table_offset, TRUE); |
832 | break; | 839 | set_bit(table_index, acpi_initrd_installed); |
833 | } while (table_offset + ACPI_HEADER_SIZE < all_tables_size); | 840 | next_table: |
841 | table_offset += table_length; | ||
842 | table_index++; | ||
843 | } | ||
844 | } | ||
845 | #else | ||
846 | acpi_status | ||
847 | acpi_os_physical_table_override(struct acpi_table_header *existing_table, | ||
848 | acpi_physical_address *address, | ||
849 | u32 *table_length) | ||
850 | { | ||
851 | *table_length = 0; | ||
852 | *address = 0; | ||
853 | return AE_OK; | ||
854 | } | ||
855 | |||
856 | void __init acpi_initrd_initialize_tables(void) | ||
857 | { | ||
858 | } | ||
859 | #endif /* CONFIG_ACPI_INITRD_TABLE_OVERRIDE */ | ||
834 | 860 | ||
835 | if (*address != 0) | 861 | acpi_status |
862 | acpi_os_table_override(struct acpi_table_header *existing_table, | ||
863 | struct acpi_table_header **new_table) | ||
864 | { | ||
865 | if (!existing_table || !new_table) | ||
866 | return AE_BAD_PARAMETER; | ||
867 | |||
868 | *new_table = NULL; | ||
869 | |||
870 | #ifdef CONFIG_ACPI_CUSTOM_DSDT | ||
871 | if (strncmp(existing_table->signature, "DSDT", 4) == 0) | ||
872 | *new_table = (struct acpi_table_header *)AmlCode; | ||
873 | #endif | ||
874 | if (*new_table != NULL) | ||
836 | acpi_table_taint(existing_table); | 875 | acpi_table_taint(existing_table); |
837 | return AE_OK; | 876 | return AE_OK; |
838 | #endif | ||
839 | } | 877 | } |
840 | 878 | ||
841 | static irqreturn_t acpi_irq(int irq, void *dev_id) | 879 | static irqreturn_t acpi_irq(int irq, void *dev_id) |
diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index 407a3760e8de..5f28cf778349 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c | |||
@@ -1930,6 +1930,7 @@ int __init acpi_scan_init(void) | |||
1930 | acpi_memory_hotplug_init(); | 1930 | acpi_memory_hotplug_init(); |
1931 | acpi_pnp_init(); | 1931 | acpi_pnp_init(); |
1932 | acpi_int340x_thermal_init(); | 1932 | acpi_int340x_thermal_init(); |
1933 | acpi_amba_init(); | ||
1933 | 1934 | ||
1934 | acpi_scan_add_handler(&generic_device_handler); | 1935 | acpi_scan_add_handler(&generic_device_handler); |
1935 | 1936 | ||
diff --git a/drivers/acpi/tables.c b/drivers/acpi/tables.c index 6c0f0794aa82..57c0a4525dba 100644 --- a/drivers/acpi/tables.c +++ b/drivers/acpi/tables.c | |||
@@ -32,6 +32,7 @@ | |||
32 | #include <linux/errno.h> | 32 | #include <linux/errno.h> |
33 | #include <linux/acpi.h> | 33 | #include <linux/acpi.h> |
34 | #include <linux/bootmem.h> | 34 | #include <linux/bootmem.h> |
35 | #include "internal.h" | ||
35 | 36 | ||
36 | #define ACPI_MAX_TABLES 128 | 37 | #define ACPI_MAX_TABLES 128 |
37 | 38 | ||
@@ -456,6 +457,7 @@ int __init acpi_table_init(void) | |||
456 | status = acpi_initialize_tables(initial_tables, ACPI_MAX_TABLES, 0); | 457 | status = acpi_initialize_tables(initial_tables, ACPI_MAX_TABLES, 0); |
457 | if (ACPI_FAILURE(status)) | 458 | if (ACPI_FAILURE(status)) |
458 | return -EINVAL; | 459 | return -EINVAL; |
460 | acpi_initrd_initialize_tables(); | ||
459 | 461 | ||
460 | check_multiple_madt(); | 462 | check_multiple_madt(); |
461 | return 0; | 463 | return 0; |