dm: core: Add a way to obtain a string list

At present we support reading a string list a string at a time. Apart
from being inefficient, this makes it impossible to separate reading of
the devicetree into the of_to_plat() method where it belongs, since any
code which needs access to the string must read it from the devicetree.

Add a function which returns the string property as an array of pointers
to the strings, which is easily used by clients.

Signed-off-by: Simon Glass <sjg@chromium.org>
diff --git a/include/dm/ofnode.h b/include/dm/ofnode.h
index 0eae8f9..6601bd8 100644
--- a/include/dm/ofnode.h
+++ b/include/dm/ofnode.h
@@ -610,6 +610,26 @@
 int ofnode_read_string_count(ofnode node, const char *property);
 
 /**
+ * ofnode_read_string_list() - read a list of strings
+ *
+ * This produces a list of string pointers with each one pointing to a string
+ * in the string list. If the property does not exist, it returns {NULL}.
+ *
+ * The data is allocated and the caller is reponsible for freeing the return
+ * value (the list of string pointers). The strings themselves may not be
+ * changed as they point directly into the devicetree property.
+ *
+ * @node: node to check
+ * @listp: returns an allocated, NULL-terminated list of strings if the return
+ *	value is > 0, else is set to NULL
+ * @return number of strings in list, 0 if none, -ENOMEM if out of memory,
+ *	-EINVAL if no such property, -EENODATA if property is empty
+ * @return: NULL-terminated list of strings (NULL if no property or empty)
+ */
+int ofnode_read_string_list(ofnode node, const char *property,
+			    const char ***listp);
+
+/**
  * ofnode_parse_phandle_with_args() - Find a node pointed by phandle in a list
  *
  * This function is useful to parse lists of phandles and their arguments.
diff --git a/include/dm/read.h b/include/dm/read.h
index 890bf3d..75c6ad6 100644
--- a/include/dm/read.h
+++ b/include/dm/read.h
@@ -371,6 +371,27 @@
  *   number of strings in the list, or -ve error value if not found
  */
 int dev_read_string_count(const struct udevice *dev, const char *propname);
+
+/**
+ * dev_read_string_list() - read a list of strings
+ *
+ * This produces a list of string pointers with each one pointing to a string
+ * in the string list. If the property does not exist, it returns {NULL}.
+ *
+ * The data is allocated and the caller is reponsible for freeing the return
+ * value (the list of string pointers). The strings themselves may not be
+ * changed as they point directly into the devicetree property.
+ *
+ * @dev: device to examine
+ * @propname: name of the property containing the string list
+ * @listp: returns an allocated, NULL-terminated list of strings if the return
+ *	value is > 0, else is set to NULL
+ * @return number of strings in list, 0 if none, -ENOMEM if out of memory,
+ *	-ENOENT if no such property
+ */
+int dev_read_string_list(const struct udevice *dev, const char *propname,
+			 const char ***listp);
+
 /**
  * dev_read_phandle_with_args() - Find a node pointed by phandle in a list
  *
@@ -906,6 +927,13 @@
 	return ofnode_read_string_count(dev_ofnode(dev), propname);
 }
 
+static inline int dev_read_string_list(const struct udevice *dev,
+				       const char *propname,
+				       const char ***listp)
+{
+	return ofnode_read_string_list(dev_ofnode(dev), propname, listp);
+}
+
 static inline int dev_read_phandle_with_args(const struct udevice *dev,
 		const char *list_name, const char *cells_name, int cell_count,
 		int index, struct ofnode_phandle_args *out_args)