device property: Introduce fwnode_for_each_parent_node()
authorAndy Shevchenko <andriy.shevchenko@linux.intel.com>
Fri, 8 Apr 2022 18:48:41 +0000 (21:48 +0300)
committerRafael J. Wysocki <rafael.j.wysocki@intel.com>
Wed, 13 Apr 2022 18:04:02 +0000 (20:04 +0200)
In a few cases the functionality of fwnode_for_each_parent_node()
is already in use. Introduce a common helper macro for it.

It may be used by others as well in the future.

Signed-off-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Reviewed-by: Sakari Ailus <sakari.ailus@linux.intel.com>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
drivers/base/property.c
include/linux/property.h

index 6ecc139..f0ac31d 100644 (file)
@@ -596,17 +596,17 @@ EXPORT_SYMBOL_GPL(fwnode_get_next_parent);
  */
 struct device *fwnode_get_next_parent_dev(struct fwnode_handle *fwnode)
 {
+       struct fwnode_handle *parent;
        struct device *dev;
 
-       fwnode_handle_get(fwnode);
-       do {
-               fwnode = fwnode_get_next_parent(fwnode);
-               if (!fwnode)
-                       return NULL;
+       fwnode_for_each_parent_node(fwnode, parent) {
                dev = get_dev_from_fwnode(fwnode);
-       } while (!dev);
-       fwnode_handle_put(fwnode);
-       return dev;
+               if (dev) {
+                       fwnode_handle_put(parent);
+                       return dev;
+               }
+       }
+       return NULL;
 }
 
 /**
@@ -617,13 +617,11 @@ struct device *fwnode_get_next_parent_dev(struct fwnode_handle *fwnode)
  */
 unsigned int fwnode_count_parents(const struct fwnode_handle *fwnode)
 {
-       struct fwnode_handle *__fwnode;
-       unsigned int count;
-
-       __fwnode = fwnode_get_parent(fwnode);
+       struct fwnode_handle *parent;
+       unsigned int count = 0;
 
-       for (count = 0; __fwnode; count++)
-               __fwnode = fwnode_get_next_parent(__fwnode);
+       fwnode_for_each_parent_node(fwnode, parent)
+               count++;
 
        return count;
 }
@@ -644,15 +642,16 @@ EXPORT_SYMBOL_GPL(fwnode_count_parents);
 struct fwnode_handle *fwnode_get_nth_parent(struct fwnode_handle *fwnode,
                                            unsigned int depth)
 {
-       fwnode_handle_get(fwnode);
+       struct fwnode_handle *parent;
 
-       do {
-               if (depth-- == 0)
-                       break;
-               fwnode = fwnode_get_next_parent(fwnode);
-       } while (fwnode);
+       if (depth == 0)
+               return fwnode_handle_get(fwnode);
 
-       return fwnode;
+       fwnode_for_each_parent_node(fwnode, parent) {
+               if (--depth == 0)
+                       return parent;
+       }
+       return NULL;
 }
 EXPORT_SYMBOL_GPL(fwnode_get_nth_parent);
 
@@ -669,17 +668,20 @@ EXPORT_SYMBOL_GPL(fwnode_get_nth_parent);
 bool fwnode_is_ancestor_of(struct fwnode_handle *test_ancestor,
                                  struct fwnode_handle *test_child)
 {
+       struct fwnode_handle *parent;
+
        if (IS_ERR_OR_NULL(test_ancestor))
                return false;
 
-       fwnode_handle_get(test_child);
-       do {
-               if (test_child == test_ancestor) {
-                       fwnode_handle_put(test_child);
+       if (test_child == test_ancestor)
+               return true;
+
+       fwnode_for_each_parent_node(test_child, parent) {
+               if (parent == test_ancestor) {
+                       fwnode_handle_put(parent);
                        return true;
                }
-               test_child = fwnode_get_next_parent(test_child);
-       } while (test_child);
+       }
        return false;
 }
 
index 4cd4b32..15d6863 100644 (file)
@@ -83,9 +83,14 @@ struct fwnode_handle *fwnode_find_reference(const struct fwnode_handle *fwnode,
 
 const char *fwnode_get_name(const struct fwnode_handle *fwnode);
 const char *fwnode_get_name_prefix(const struct fwnode_handle *fwnode);
+
 struct fwnode_handle *fwnode_get_parent(const struct fwnode_handle *fwnode);
-struct fwnode_handle *fwnode_get_next_parent(
-       struct fwnode_handle *fwnode);
+struct fwnode_handle *fwnode_get_next_parent(struct fwnode_handle *fwnode);
+
+#define fwnode_for_each_parent_node(fwnode, parent)            \
+       for (parent = fwnode_get_parent(fwnode); parent;        \
+            parent = fwnode_get_next_parent(parent))
+
 struct device *fwnode_get_next_parent_dev(struct fwnode_handle *fwnode);
 unsigned int fwnode_count_parents(const struct fwnode_handle *fwn);
 struct fwnode_handle *fwnode_get_nth_parent(struct fwnode_handle *fwn,