Skip to content

Commit

Permalink
linux: support device-tree serdes equalization parameters
Browse files Browse the repository at this point in the history
  • Loading branch information
Josua-SR committed Feb 22, 2025
1 parent 2487def commit 1d73b71
Show file tree
Hide file tree
Showing 8 changed files with 1,071 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,82 @@
From 90603740ecfd8a087213fa7763540e0bd2b6ffd7 Mon Sep 17 00:00:00 2001
From: Josua Mayer <josua@solid-run.com>
Date: Fri, 21 Feb 2025 14:34:32 +0100
Subject: [PATCH 28/35] Revert "phy: lynx-28g: add support for specifying
unmanaged lanes"

This reverts commit 7c9762a97177fe98b27c9ea76ad6a6b1287d2692.
---
.../devicetree/bindings/phy/fsl,lynx-28g.yaml | 6 ------
drivers/phy/freescale/phy-fsl-lynx-28g.c | 19 +------------------
2 files changed, 1 insertion(+), 24 deletions(-)

diff --git a/Documentation/devicetree/bindings/phy/fsl,lynx-28g.yaml b/Documentation/devicetree/bindings/phy/fsl,lynx-28g.yaml
index 71ff57927e32..4d91e2f4f247 100644
--- a/Documentation/devicetree/bindings/phy/fsl,lynx-28g.yaml
+++ b/Documentation/devicetree/bindings/phy/fsl,lynx-28g.yaml
@@ -20,12 +20,6 @@ properties:
"#phy-cells":
const: 1

- fsl,unmanaged-lanes:
- $ref: /schemas/types.yaml#definitions/uint8
- description: Select which lanes not to touch via bitmask: 0 = managed by driver, 1 = unmanaged.
- minimum: 0
- maximum: 255
-
required:
- compatible
- reg
diff --git a/drivers/phy/freescale/phy-fsl-lynx-28g.c b/drivers/phy/freescale/phy-fsl-lynx-28g.c
index e7a9a6499fd0..2152066f2dbc 100644
--- a/drivers/phy/freescale/phy-fsl-lynx-28g.c
+++ b/drivers/phy/freescale/phy-fsl-lynx-28g.c
@@ -5,7 +5,6 @@
#include <linux/phy.h>
#include <linux/phy/phy.h>
#include <linux/platform_device.h>
-#include <linux/property.h>
#include <linux/workqueue.h>
#include <linux/workqueue.h>

@@ -645,9 +644,7 @@ static int lynx_28g_probe(struct platform_device *pdev)
struct device *dev = &pdev->dev;
struct phy_provider *provider;
struct lynx_28g_priv *priv;
- struct fwnode_handle *fwnode;
- int i, ret;
- u32 unmanaged_lanes;
+ int i;

priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL);
if (!priv)
@@ -658,26 +655,12 @@ static int lynx_28g_probe(struct platform_device *pdev)
if (IS_ERR(priv->base))
return PTR_ERR(priv->base);

- fwnode = dev_fwnode(dev);
- if (fwnode && is_of_node(fwnode)) {
- ret = of_property_read_u32(to_of_node(fwnode), "fsl,unmanaged-lanes", &unmanaged_lanes);
- if (ret && ret != -EINVAL) {
- dev_err(dev, "failed to read fsl,unmanaged-lanes property: %d\n", ret);
- return ret;
- }
- }
-
lynx_28g_pll_read_configuration(priv);

for (i = 0; i < LYNX_28G_NUM_LANE; i++) {
struct lynx_28g_lane *lane = &priv->lane[i];
struct phy *phy;

- if (unmanaged_lanes & (1 << i)) {
- dev_info(dev, "unmanaged lane %d!\n", i);
- continue;
- }
-
memset(lane, 0, sizeof(*lane));

phy = devm_phy_create(&pdev->dev, NULL, &lynx_28g_ops);
--
2.43.0

Original file line number Diff line number Diff line change
@@ -0,0 +1,173 @@
From 4b63feb4d9ba0da627949c3c268fd50ff2af452d Mon Sep 17 00:00:00 2001
From: Josua Mayer <josua@solid-run.com>
Date: Fri, 21 Feb 2025 16:43:37 +0100
Subject: [PATCH 29/35] device property: add function to lookup a string from
array by index

Sometimes drivers need to access individual elements from an array of
string. of.h already provides a suitable function which is specific to
device-tree.

Add a new function device_property_read_string_index similar to the
existing device_property_read_* functions that can look-up a specific
index inside a multiple string property.

Signed-off-by: Josua Mayer <josua@solid-run.com>
---
drivers/base/property.c | 55 ++++++++++++++++++++++++++++++++++++++++
drivers/of/property.c | 11 ++++++++
include/linux/fwnode.h | 5 ++++
include/linux/property.h | 5 ++++
4 files changed, 76 insertions(+)

diff --git a/drivers/base/property.c b/drivers/base/property.c
index 735a23db1b5e..3d192e237e93 100644
--- a/drivers/base/property.c
+++ b/drivers/base/property.c
@@ -206,6 +206,29 @@ int device_property_read_string(struct device *dev, const char *propname,
}
EXPORT_SYMBOL_GPL(device_property_read_string);

+/**
+ * device_property_read_string_index - find a string in an array by index
+ * @dev: Device to get the property of
+ * @propname: Name of the property holding the array
+ * @index: The index of the string in the list of strings
+ * @val: The value is stored here
+ *
+ * Finds given index in a string array and stores the value into @val
+ * if found.
+ *
+ * Return: %0 if the string was found (success),
+ * %-EINVAL if given arguments are not valid,
+ * %-ENODATA if the property does not have a value,
+ * %-EPROTO or %-EILSEQ if the property type is not a string.
+ * %-ENXIO if no suitable firmware interface is present.
+ */
+int device_property_read_string_index(struct device *dev, const char *propname,
+ int index, const char **val)
+{
+ return fwnode_property_read_string_index(dev_fwnode(dev), propname, index, val);
+}
+EXPORT_SYMBOL_GPL(device_property_read_string_index);
+
/**
* device_property_match_string - find a string in an array and return index
* @dev: Device to get the property of
@@ -412,6 +435,38 @@ int fwnode_property_read_string(const struct fwnode_handle *fwnode,
}
EXPORT_SYMBOL_GPL(fwnode_property_read_string);

+/**
+ * fwnode_property_read_string_index - find a string in an array by index
+ * @fwnode: Firmware node to get the property of
+ * @propname: Name of the property holding the array
+ * @index: The index of the string in the list of strings
+ * @val: The value is stored here
+ *
+ * Read property @propname from the given firmware node and store the value into
+ * @val if found. The value is checked to be a string.
+ *
+ * Return: %0 if the string was found (success),
+ * %-EINVAL if given arguments are not valid,
+ * %-ENODATA if the property does not have a value,
+ * %-EPROTO or %-EILSEQ if the property is not a string,
+ * %-ENXIO if no suitable firmware interface is present.
+ */
+int fwnode_property_read_string_index(const struct fwnode_handle *fwnode,
+ const char *propname, int index,
+ const char **val)
+{
+ int ret;
+
+ if (IS_ERR_OR_NULL(fwnode))
+ return -EINVAL;
+
+ ret = fwnode_call_int_op(fwnode, property_read_string_index, propname,
+ index, val);
+
+ return ret < 0 ? ret : 0;
+}
+EXPORT_SYMBOL_GPL(fwnode_property_read_string_index);
+
/**
* fwnode_property_match_string - find a string in an array and return index
* @fwnode: Firmware node to get the property of
diff --git a/drivers/of/property.c b/drivers/of/property.c
index c1768719ee89..6ffcdec20db1 100644
--- a/drivers/of/property.c
+++ b/drivers/of/property.c
@@ -915,6 +915,16 @@ of_fwnode_property_read_string_array(const struct fwnode_handle *fwnode,
of_property_count_strings(node, propname);
}

+static int
+of_fwnode_property_read_string_index(const struct fwnode_handle *fwnode,
+ const char *propname, int index,
+ const char **val)
+{
+ const struct device_node *node = to_of_node(fwnode);
+
+ return of_property_read_string_index(node, propname, index, val);
+}
+
static const char *of_fwnode_get_name(const struct fwnode_handle *fwnode)
{
return kbasename(to_of_node(fwnode)->full_name);
@@ -1462,6 +1472,7 @@ const struct fwnode_operations of_fwnode_ops = {
.property_present = of_fwnode_property_present,
.property_read_int_array = of_fwnode_property_read_int_array,
.property_read_string_array = of_fwnode_property_read_string_array,
+ .property_read_string_index = of_fwnode_property_read_string_index,
.get_name = of_fwnode_get_name,
.get_name_prefix = of_fwnode_get_name_prefix,
.get_parent = of_fwnode_get_parent,
diff --git a/include/linux/fwnode.h b/include/linux/fwnode.h
index 2d68606fb725..06ce0cb8759d 100644
--- a/include/linux/fwnode.h
+++ b/include/linux/fwnode.h
@@ -92,6 +92,7 @@ struct fwnode_reference_args {
* success, a negative error code otherwise.
* @property_read_string_array: Read an array of string properties. Return zero
* on success, a negative error code otherwise.
+ * @property_read_string_index: Find a string in an array by index.
* @get_name: Return the name of an fwnode.
* @get_name_prefix: Get a prefix for a node (for printing purposes).
* @get_parent: Return the parent of an fwnode.
@@ -122,6 +123,10 @@ struct fwnode_operations {
(*property_read_string_array)(const struct fwnode_handle *fwnode_handle,
const char *propname, const char **val,
size_t nval);
+ int
+ (*property_read_string_index)(const struct fwnode_handle *fwnode_handle,
+ const char *propname, int index,
+ const char **val);
const char *(*get_name)(const struct fwnode_handle *fwnode);
const char *(*get_name_prefix)(const struct fwnode_handle *fwnode);
struct fwnode_handle *(*get_parent)(const struct fwnode_handle *fwnode);
diff --git a/include/linux/property.h b/include/linux/property.h
index 357513a977e5..c66b6b9f0dcd 100644
--- a/include/linux/property.h
+++ b/include/linux/property.h
@@ -46,6 +46,8 @@ int device_property_read_string_array(struct device *dev, const char *propname,
const char **val, size_t nval);
int device_property_read_string(struct device *dev, const char *propname,
const char **val);
+int device_property_read_string_index(struct device *dev, const char *propname,
+ int index,const char **val);
int device_property_match_string(struct device *dev,
const char *propname, const char *string);

@@ -69,6 +71,9 @@ int fwnode_property_read_string_array(const struct fwnode_handle *fwnode,
size_t nval);
int fwnode_property_read_string(const struct fwnode_handle *fwnode,
const char *propname, const char **val);
+int fwnode_property_read_string_index(const struct fwnode_handle *fwnode,
+ const char *propname, int index,
+ const char **val);
int fwnode_property_match_string(const struct fwnode_handle *fwnode,
const char *propname, const char *string);
int fwnode_property_get_reference_args(const struct fwnode_handle *fwnode,
--
2.43.0

Loading

0 comments on commit 1d73b71

Please sign in to comment.