resources: Move struct resource_list_entry from ACPI into resource core
authorJiang Liu <jiang.liu@linux.intel.com>
Thu, 5 Feb 2015 05:44:43 +0000 (13:44 +0800)
committerRafael J. Wysocki <rafael.j.wysocki@intel.com>
Thu, 5 Feb 2015 14:09:25 +0000 (15:09 +0100)
Currently ACPI, PCI and pnp all implement the same resource list
management with different data structure. We need to transfer from
one data structure into another when passing resources from one
subsystem into another subsystem. So move struct resource_list_entry
from ACPI into resource core and rename it as resource_entry,
then it could be reused by different subystems and avoid the data
structure conversion.

Introduce dedicated header file resource_ext.h instead of embedding
it into ioport.h to avoid header file inclusion order issues.

Signed-off-by: Jiang Liu <jiang.liu@linux.intel.com>
Acked-by: Vinod Koul <vinod.koul@intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
drivers/acpi/acpi_lpss.c
drivers/acpi/acpi_platform.c
drivers/acpi/resource.c
drivers/dma/acpi-dma.c
include/linux/acpi.h
include/linux/resource_ext.h [new file with mode: 0644]
kernel/resource.c

index 4f3febf8a58954b2ca8ced8c057106529ab1f30b..dfd1b8095dadbb6c853dc98e669c21eeeff60bb3 100644 (file)
@@ -313,7 +313,7 @@ static int acpi_lpss_create_device(struct acpi_device *adev,
 {
        struct lpss_device_desc *dev_desc;
        struct lpss_private_data *pdata;
-       struct resource_list_entry *rentry;
+       struct resource_entry *rentry;
        struct list_head resource_list;
        struct platform_device *pdev;
        int ret;
@@ -333,12 +333,12 @@ static int acpi_lpss_create_device(struct acpi_device *adev,
                goto err_out;
 
        list_for_each_entry(rentry, &resource_list, node)
-               if (resource_type(&rentry->res) == IORESOURCE_MEM) {
+               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 = resource_size(rentry->res);
+                       pdata->mmio_base = ioremap(rentry->res->start,
                                                   pdata->mmio_size);
                        break;
                }
index 6ba8beb6b9d2a515828c3987393dc75fa8b6bc2c..1284138e42ab486d584f61e3f90bbaf0320a1a5b 100644 (file)
@@ -45,7 +45,7 @@ struct platform_device *acpi_create_platform_device(struct acpi_device *adev)
        struct platform_device *pdev = NULL;
        struct acpi_device *acpi_parent;
        struct platform_device_info pdevinfo;
-       struct resource_list_entry *rentry;
+       struct resource_entry *rentry;
        struct list_head resource_list;
        struct resource *resources = NULL;
        int count;
@@ -71,7 +71,7 @@ struct platform_device *acpi_create_platform_device(struct acpi_device *adev)
                }
                count = 0;
                list_for_each_entry(rentry, &resource_list, node)
-                       resources[count++] = rentry->res;
+                       resources[count++] = *rentry->res;
 
                acpi_dev_free_resource_list(&resource_list);
        }
index 3ea0d17eb95178474b0e231af3ad3e4b25d166e3..4752b99399870efd068a1f1a6c656b1ebe333349 100644 (file)
@@ -444,12 +444,7 @@ EXPORT_SYMBOL_GPL(acpi_dev_resource_interrupt);
  */
 void acpi_dev_free_resource_list(struct list_head *list)
 {
-       struct resource_list_entry *rentry, *re;
-
-       list_for_each_entry_safe(rentry, re, list, node) {
-               list_del(&rentry->node);
-               kfree(rentry);
-       }
+       resource_list_free(list);
 }
 EXPORT_SYMBOL_GPL(acpi_dev_free_resource_list);
 
@@ -464,16 +459,16 @@ struct res_proc_context {
 static acpi_status acpi_dev_new_resource_entry(struct resource_win *win,
                                               struct res_proc_context *c)
 {
-       struct resource_list_entry *rentry;
+       struct resource_entry *rentry;
 
-       rentry = kmalloc(sizeof(*rentry), GFP_KERNEL);
+       rentry = resource_list_create_entry(NULL, 0);
        if (!rentry) {
                c->error = -ENOMEM;
                return AE_NO_MEMORY;
        }
-       rentry->res = win->res;
+       *rentry->res = win->res;
        rentry->offset = win->offset;
-       list_add_tail(&rentry->node, c->list);
+       resource_list_add_tail(rentry, c->list);
        c->count++;
        return AE_OK;
 }
@@ -534,7 +529,7 @@ static acpi_status acpi_dev_process_resource(struct acpi_resource *ares,
  * returned as the final error code.
  *
  * The resultant struct resource objects are put on the list pointed to by
- * @list, that must be empty initially, as members of struct resource_list_entry
+ * @list, that must be empty initially, as members of struct resource_entry
  * objects.  Callers of this routine should use %acpi_dev_free_resource_list() to
  * free that list.
  *
index de361a156b341ab85a0b22490f2ff9407c93ce30..5a635646e05cfe87a9f92083c5864827c669ccee 100644 (file)
@@ -43,7 +43,7 @@ static int acpi_dma_parse_resource_group(const struct acpi_csrt_group *grp,
 {
        const struct acpi_csrt_shared_info *si;
        struct list_head resource_list;
-       struct resource_list_entry *rentry;
+       struct resource_entry *rentry;
        resource_size_t mem = 0, irq = 0;
        int ret;
 
@@ -56,10 +56,10 @@ static int acpi_dma_parse_resource_group(const struct acpi_csrt_group *grp,
                return 0;
 
        list_for_each_entry(rentry, &resource_list, node) {
-               if (resource_type(&rentry->res) == IORESOURCE_MEM)
-                       mem = rentry->res.start;
-               else if (resource_type(&rentry->res) == IORESOURCE_IRQ)
-                       irq = rentry->res.start;
+               if (resource_type(rentry->res) == IORESOURCE_MEM)
+                       mem = rentry->res->start;
+               else if (resource_type(rentry->res) == IORESOURCE_IRQ)
+                       irq = rentry->res->start;
        }
 
        acpi_dev_free_resource_list(&resource_list);
index e818decb631fb39d6bc18d7678affd234ee300de..e53822148b6a0542b0322aaa6729e6c4c569978f 100644 (file)
@@ -27,6 +27,7 @@
 
 #include <linux/errno.h>
 #include <linux/ioport.h>      /* for struct resource */
+#include <linux/resource_ext.h>
 #include <linux/device.h>
 #include <linux/property.h>
 
@@ -285,11 +286,6 @@ extern int pnpacpi_disabled;
 
 #define PXM_INVAL      (-1)
 
-struct resource_win {
-       struct resource res;
-       resource_size_t offset;
-};
-
 bool acpi_dev_resource_memory(struct acpi_resource *ares, struct resource *res);
 bool acpi_dev_resource_io(struct acpi_resource *ares, struct resource *res);
 bool acpi_dev_resource_address_space(struct acpi_resource *ares,
@@ -300,12 +296,6 @@ unsigned long acpi_dev_irq_flags(u8 triggering, u8 polarity, u8 shareable);
 bool acpi_dev_resource_interrupt(struct acpi_resource *ares, int index,
                                 struct resource *res);
 
-struct resource_list_entry {
-       struct list_head node;
-       struct resource res;
-       resource_size_t offset;
-};
-
 void acpi_dev_free_resource_list(struct list_head *list);
 int acpi_dev_get_resources(struct acpi_device *adev, struct list_head *list,
                           int (*preproc)(struct acpi_resource *, void *),
diff --git a/include/linux/resource_ext.h b/include/linux/resource_ext.h
new file mode 100644 (file)
index 0000000..e2bf63d
--- /dev/null
@@ -0,0 +1,77 @@
+/*
+ * Copyright (C) 2015, Intel Corporation
+ * Author: Jiang Liu <jiang.liu@linux.intel.com>
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope 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.
+ */
+#ifndef _LINUX_RESOURCE_EXT_H
+#define _LINUX_RESOURCE_EXT_H
+#include <linux/types.h>
+#include <linux/list.h>
+#include <linux/ioport.h>
+#include <linux/slab.h>
+
+/* Represent resource window for bridge devices */
+struct resource_win {
+       struct resource res;            /* In master (CPU) address space */
+       resource_size_t offset;         /* Translation offset for bridge */
+};
+
+/*
+ * Common resource list management data structure and interfaces to support
+ * ACPI, PNP and PCI host bridge etc.
+ */
+struct resource_entry {
+       struct list_head        node;
+       struct resource         *res;   /* In master (CPU) address space */
+       resource_size_t         offset; /* Translation offset for bridge */
+       struct resource         __res;  /* Default storage for res */
+};
+
+extern struct resource_entry *
+resource_list_create_entry(struct resource *res, size_t extra_size);
+extern void resource_list_free(struct list_head *head);
+
+static inline void resource_list_add(struct resource_entry *entry,
+                                    struct list_head *head)
+{
+       list_add(&entry->node, head);
+}
+
+static inline void resource_list_add_tail(struct resource_entry *entry,
+                                         struct list_head *head)
+{
+       list_add_tail(&entry->node, head);
+}
+
+static inline void resource_list_del(struct resource_entry *entry)
+{
+       list_del(&entry->node);
+}
+
+static inline void resource_list_free_entry(struct resource_entry *entry)
+{
+       kfree(entry);
+}
+
+static inline void
+resource_list_destroy_entry(struct resource_entry *entry)
+{
+       resource_list_del(entry);
+       resource_list_free_entry(entry);
+}
+
+#define resource_list_for_each_entry(entry, list)      \
+       list_for_each_entry((entry), (list), node)
+
+#define resource_list_for_each_entry_safe(entry, tmp, list)    \
+       list_for_each_entry_safe((entry), (tmp), (list), node)
+
+#endif /* _LINUX_RESOURCE_EXT_H */
index 0bcebffc4e77d5f45571e38ddc5dcc38f40594f4..19f2357dfda3fe88f7e0ddc6b29778176138a619 100644 (file)
@@ -22,6 +22,7 @@
 #include <linux/device.h>
 #include <linux/pfn.h>
 #include <linux/mm.h>
+#include <linux/resource_ext.h>
 #include <asm/io.h>
 
 
@@ -1529,6 +1530,30 @@ int iomem_is_exclusive(u64 addr)
        return err;
 }
 
+struct resource_entry *resource_list_create_entry(struct resource *res,
+                                                 size_t extra_size)
+{
+       struct resource_entry *entry;
+
+       entry = kzalloc(sizeof(*entry) + extra_size, GFP_KERNEL);
+       if (entry) {
+               INIT_LIST_HEAD(&entry->node);
+               entry->res = res ? res : &entry->__res;
+       }
+
+       return entry;
+}
+EXPORT_SYMBOL(resource_list_create_entry);
+
+void resource_list_free(struct list_head *head)
+{
+       struct resource_entry *entry, *tmp;
+
+       list_for_each_entry_safe(entry, tmp, head, node)
+               resource_list_destroy_entry(entry);
+}
+EXPORT_SYMBOL(resource_list_free);
+
 static int __init strict_iomem(char *str)
 {
        if (strstr(str, "relaxed"))