Commit 652d39b0 authored by Kejian Yan's avatar Kejian Yan Committed by David S. Miller

net: hns: add uniform interface for phy connection

As device_node is only used by DT case, HNS needs to treat the other
cases including ACPI. It needs to use uniform ways to handle both of
DT and ACPI. This patch chooses phy_device, and of_phy_connect and
of_phy_attach are only used by DT case. It needs to use uniform interface
to handle that sequence by both DT and ACPI.
Signed-off-by: default avatarKejian Yan <yankejian@huawei.com>
Signed-off-by: default avatarYisen Zhuang <Yisen.Zhuang@huawei.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 7b2acae6
......@@ -96,7 +96,13 @@ static int __ae_match(struct device *dev, const void *data)
{
struct hnae_ae_dev *hdev = cls_to_ae_dev(dev);
if (dev_of_node(hdev->dev))
return (data == &hdev->dev->of_node->fwnode);
else if (is_acpi_node(hdev->dev->fwnode))
return (data == hdev->dev->fwnode);
dev_err(dev, "__ae_match cannot read cfg data from OF or acpi\n");
return 0;
}
static struct hnae_ae_dev *find_ae(const struct fwnode_handle *fwnode)
......
......@@ -27,6 +27,7 @@
* "cb" means control block
*/
#include <linux/acpi.h>
#include <linux/delay.h>
#include <linux/device.h>
#include <linux/module.h>
......@@ -512,7 +513,7 @@ struct hnae_ae_dev {
struct hnae_handle {
struct device *owner_dev; /* the device which make use of this handle */
struct hnae_ae_dev *dev; /* the device who provides this handle */
struct device_node *phy_node;
struct phy_device *phy_dev;
phy_interface_t phy_if;
u32 if_support;
int q_num;
......
......@@ -131,7 +131,7 @@ struct hnae_handle *hns_ae_get_handle(struct hnae_ae_dev *dev,
vf_cb->mac_cb = dsaf_dev->mac_cb[port_id];
ae_handle->phy_if = vf_cb->mac_cb->phy_if;
ae_handle->phy_node = vf_cb->mac_cb->phy_node;
ae_handle->phy_dev = vf_cb->mac_cb->phy_dev;
ae_handle->if_support = vf_cb->mac_cb->if_support;
ae_handle->port_type = vf_cb->mac_cb->mac_type;
ae_handle->dport_id = port_id;
......
......@@ -15,7 +15,8 @@
#include <linux/netdevice.h>
#include <linux/of.h>
#include <linux/of_address.h>
#include <linux/phy_fixed.h>
#include <linux/of_mdio.h>
#include <linux/phy.h>
#include <linux/platform_device.h>
#include "hns_dsaf_main.h"
......@@ -645,7 +646,7 @@ static int hns_mac_init_ex(struct hns_mac_cb *mac_cb)
*/
static int hns_mac_get_info(struct hns_mac_cb *mac_cb)
{
struct device_node *np = mac_cb->dev->of_node;
struct device_node *np;
struct regmap *syscon;
struct of_phandle_args cpld_args;
u32 ret;
......@@ -672,21 +673,34 @@ static int hns_mac_get_info(struct hns_mac_cb *mac_cb)
* from dsaf node
*/
if (!mac_cb->fw_port) {
mac_cb->phy_node = of_parse_phandle(np, "phy-handle",
np = of_parse_phandle(mac_cb->dev->of_node, "phy-handle",
mac_cb->mac_id);
if (mac_cb->phy_node)
mac_cb->phy_dev = of_phy_find_device(np);
if (mac_cb->phy_dev) {
/* refcount is held by of_phy_find_device()
* if the phy_dev is found
*/
put_device(&mac_cb->phy_dev->mdio.dev);
dev_dbg(mac_cb->dev, "mac%d phy_node: %s\n",
mac_cb->mac_id, mac_cb->phy_node->name);
mac_cb->mac_id, np->name);
}
return 0;
}
if (!is_of_node(mac_cb->fw_port))
return -EINVAL;
/* parse property from port subnode in dsaf */
mac_cb->phy_node = of_parse_phandle(to_of_node(mac_cb->fw_port),
"phy-handle", 0);
if (mac_cb->phy_node)
np = of_parse_phandle(to_of_node(mac_cb->fw_port), "phy-handle", 0);
mac_cb->phy_dev = of_phy_find_device(np);
if (mac_cb->phy_dev) {
put_device(&mac_cb->phy_dev->mdio.dev);
dev_dbg(mac_cb->dev, "mac%d phy_node: %s\n",
mac_cb->mac_id, mac_cb->phy_node->name);
mac_cb->mac_id, np->name);
}
syscon = syscon_node_to_regmap(
of_parse_phandle(to_of_node(mac_cb->fw_port),
"serdes-syscon", 0));
......
......@@ -338,7 +338,7 @@ struct hns_mac_cb {
phy_interface_t phy_if;
enum hnae_loop loop_mode;
struct device_node *phy_node;
struct phy_device *phy_dev;
struct mac_hw_stats hw_stats;
};
......
......@@ -332,7 +332,7 @@ int hns_mac_config_sds_loopback(struct hns_mac_cb *mac_cb, u8 en)
int sfp_prsnt;
int ret = hns_mac_get_sfp_prsnt(mac_cb, &sfp_prsnt);
if (!mac_cb->phy_node) {
if (!mac_cb->phy_dev) {
if (ret)
pr_info("please confirm sfp is present or not\n");
else
......
......@@ -996,19 +996,22 @@ static void hns_nic_adjust_link(struct net_device *ndev)
int hns_nic_init_phy(struct net_device *ndev, struct hnae_handle *h)
{
struct hns_nic_priv *priv = netdev_priv(ndev);
struct phy_device *phy_dev = NULL;
struct phy_device *phy_dev = h->phy_dev;
int ret;
if (!h->phy_node)
if (!h->phy_dev)
return 0;
if (h->phy_if != PHY_INTERFACE_MODE_XGMII)
phy_dev = of_phy_connect(ndev, h->phy_node,
hns_nic_adjust_link, 0, h->phy_if);
else
phy_dev = of_phy_attach(ndev, h->phy_node, 0, h->phy_if);
if (h->phy_if != PHY_INTERFACE_MODE_XGMII) {
phy_dev->dev_flags = 0;
if (unlikely(!phy_dev) || IS_ERR(phy_dev))
return !phy_dev ? -ENODEV : PTR_ERR(phy_dev);
ret = phy_connect_direct(ndev, phy_dev, hns_nic_adjust_link,
h->phy_if);
} else {
ret = phy_attach_direct(ndev, phy_dev, 0, h->phy_if);
}
if (unlikely(ret))
return -ENODEV;
phy_dev->supported &= h->if_support;
phy_dev->advertising = phy_dev->supported;
......
......@@ -596,7 +596,7 @@ static void hns_nic_self_test(struct net_device *ndev,
st_param[1][0] = MAC_INTERNALLOOP_SERDES;
st_param[1][1] = 1; /*serdes must exist*/
st_param[2][0] = MAC_INTERNALLOOP_PHY; /* only supporte phy node*/
st_param[2][1] = ((!!(priv->ae_handle->phy_node)) &&
st_param[2][1] = ((!!(priv->ae_handle->phy_dev)) &&
(priv->ae_handle->phy_if != PHY_INTERFACE_MODE_XGMII));
if (eth_test->flags == ETH_TEST_FL_OFFLINE) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment