Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > linux.kernel > #1409050 > unrolled thread
| Started by | Yisen Zhuang <Yisen.Zhuang@huawei.com> |
|---|---|
| First post | 2016-05-30 14:20 +0200 |
| Last post | 2016-05-30 14:30 +0200 |
| Articles | 4 — 1 participant |
Back to article view | Back to linux.kernel
[PATCH v3 net-next 00/13] net: hns: add support of ACPI Yisen Zhuang <Yisen.Zhuang@huawei.com> - 2016-05-30 14:20 +0200
[PATCH v3 net-next 12/13] net: hns: implement the miscellaneous operation by asl Yisen Zhuang <Yisen.Zhuang@huawei.com> - 2016-05-30 14:20 +0200
[PATCH v3 net-next 04/13] net: hisilicon: add support of acpi for hns-mdio Yisen Zhuang <Yisen.Zhuang@huawei.com> - 2016-05-30 14:30 +0200
[PATCH v3 net-next 08/13] net: hns: add uniform interface for phy connection Yisen Zhuang <Yisen.Zhuang@huawei.com> - 2016-05-30 14:30 +0200
| From | Yisen Zhuang <Yisen.Zhuang@huawei.com> |
|---|---|
| Date | 2016-05-30 14:20 +0200 |
| Subject | [PATCH v3 net-next 00/13] net: hns: add support of ACPI |
| Message-ID | <rEukN-44d-7@gated-at.bofh.it> |
From: Kejian Yan <yankejian@huawei.com>
This series adds HNS support of acpi. The routine will call some ACPI
helper functions, like acpi_dev_found() and acpi_evaluate_dsm(), which
are not included in other cases. In order to make system compile
successfully in other cases except ACPI, it needs to add relative stub
functions to linux/acpi.h. And we use device property functions instead
of serial helper functions to suport both DT and ACPI cases. And then
add the supports of ACPI for HNS.
change log:
v2->v3:
1. add Review-by: Andy Shevchenko
2. fix the potential memory leak
v1 -> v2:
1. use acpi_dev_found() instead of acpi_match_device_ids() to check if
it is a acpi node.
2. use is_of_node() instead of IS_ENABLED() to check if it is a DT node.
3. split the patch("add support of acpi for hns-mdio") into two patches:
3.1 Move to use fwnode_handle
3.2 Add ACPI
4. add the patch which subject is dsaf misc operation method
5. fix the comments by Andy Shevchenko
Kejian Yan (13):
ACPI: bus: add stub acpi_dev_found() to linux/acpi.h
ACPI: bus: add stub acpi_evaluate_dsm() to linux/acpi.h
net: hisilicon: cleanup to prepare for other cases
net: hisilicon: add support of acpi for hns-mdio
net: hns: use device_* APIs instead of of_* APIs
net: hns: use platform_get_irq instead of irq_of_parse_and_map
net: hns: enet specify a reference to dsaf by fwnode_handle
net: hns: add uniform interface for phy connection
net: hns: add dsaf misc operation method
net: hns: dsaf adds support of acpi
net: hns: register phy device in each mac initial sequence
net: hns: implement the miscellaneous operation by asl
net: hns: net: hns: enet adds support of acpi
drivers/net/ethernet/hisilicon/hns/hnae.c | 18 +-
drivers/net/ethernet/hisilicon/hns/hnae.h | 5 +-
drivers/net/ethernet/hisilicon/hns/hns_ae_adapt.c | 6 +-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_gmac.c | 6 +-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.c | 247 +++++++++++++++-----
drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.h | 4 +-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_main.c | 105 ++++++---
drivers/net/ethernet/hisilicon/hns/hns_dsaf_main.h | 33 ++-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c | 254 ++++++++++++++++++---
drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.h | 7 +-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_ppe.c | 15 +-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_rcb.c | 5 +-
.../net/ethernet/hisilicon/hns/hns_dsaf_xgmac.c | 10 +-
drivers/net/ethernet/hisilicon/hns/hns_enet.c | 90 +++++---
drivers/net/ethernet/hisilicon/hns/hns_enet.h | 2 +-
drivers/net/ethernet/hisilicon/hns/hns_ethtool.c | 2 +-
drivers/net/ethernet/hisilicon/hns_mdio.c | 147 +++++++-----
include/linux/acpi.h | 13 ++
18 files changed, 714 insertions(+), 255 deletions(-)
--
1.9.1
[toc] | [next] | [standalone]
| From | Yisen Zhuang <Yisen.Zhuang@huawei.com> |
|---|---|
| Date | 2016-05-30 14:20 +0200 |
| Subject | [PATCH v3 net-next 12/13] net: hns: implement the miscellaneous operation by asl |
| Message-ID | <rEukO-44d-29@gated-at.bofh.it> |
| In reply to | #1409050 |
From: Kejian Yan <yankejian@huawei.com>
The miscellaneous operation is implemented in BIOS, the kernel can call
_DSM method help to call the implementation in ACPI case. Here is a patch
to do that.
Signed-off-by: Kejian Yan <yankejian@huawei.com>
Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Signed-off-by: Yisen Zhuang <Yisen.Zhuang@huawei.com>
---
change log:
v3: fix potential memory leak
add Reviewed-by: Andy Shevchenko
v2: use a serial function to implement the reset sequence
link: https://lkml.org/lkml/2016/5/29/186
v1: first submit
link: https://lkml.org/lkml/2016/5/13/94
---
drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c | 171 +++++++++++++++++++++
1 file changed, 171 insertions(+)
diff --git a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c
index f21177b..6a75d81 100644
--- a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c
+++ b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c
@@ -12,6 +12,27 @@
#include "hns_dsaf_ppe.h"
#include "hns_dsaf_reg.h"
+enum _dsm_op_index {
+ HNS_OP_RESET_FUNC = 0x1,
+ HNS_OP_SERDES_LP_FUNC = 0x2,
+ HNS_OP_LED_SET_FUNC = 0x3,
+ HNS_OP_GET_PORT_TYPE_FUNC = 0x4,
+ HNS_OP_GET_SFP_STAT_FUNC = 0x5,
+};
+
+enum _dsm_rst_type {
+ HNS_DSAF_RESET_FUNC = 0x1,
+ HNS_PPE_RESET_FUNC = 0x2,
+ HNS_XGE_CORE_RESET_FUNC = 0x3,
+ HNS_XGE_RESET_FUNC = 0x4,
+ HNS_GE_RESET_FUNC = 0x5,
+};
+
+const u8 hns_dsaf_acpi_dsm_uuid[] = {
+ 0x1A, 0xAA, 0x85, 0x1A, 0x93, 0xE2, 0x5E, 0x41,
+ 0x8E, 0x28, 0x8D, 0x69, 0x0A, 0x0F, 0x82, 0x0A
+};
+
static void dsaf_write_sub(struct dsaf_device *dsaf_dev, u32 reg, u32 val)
{
if (dsaf_dev->sub_ctrl)
@@ -109,6 +130,34 @@ static int cpld_set_led_id(struct hns_mac_cb *mac_cb,
#define RESET_REQ_OR_DREQ 1
+static void hns_dsaf_acpi_srst_by_port(struct dsaf_device *dsaf_dev, u8 op_type,
+ u32 port_type, u32 port, u32 val)
+{
+ union acpi_object *obj;
+ union acpi_object obj_args[3], argv4;
+
+ obj_args[0].integer.type = ACPI_TYPE_INTEGER;
+ obj_args[0].integer.value = port_type;
+ obj_args[1].integer.type = ACPI_TYPE_INTEGER;
+ obj_args[1].integer.value = port;
+ obj_args[2].integer.type = ACPI_TYPE_INTEGER;
+ obj_args[2].integer.value = val;
+
+ argv4.type = ACPI_TYPE_PACKAGE;
+ argv4.package.count = 3;
+ argv4.package.elements = obj_args;
+
+ obj = acpi_evaluate_dsm(ACPI_HANDLE(dsaf_dev->dev),
+ hns_dsaf_acpi_dsm_uuid, 0, op_type, &argv4);
+ if (!obj) {
+ dev_warn(dsaf_dev->dev, "reset port_type%d port%d fail!",
+ port_type, port);
+ return;
+ }
+
+ ACPI_FREE(obj);
+}
+
static void hns_dsaf_rst(struct dsaf_device *dsaf_dev, bool dereset)
{
u32 xbar_reg_addr;
@@ -126,6 +175,13 @@ static void hns_dsaf_rst(struct dsaf_device *dsaf_dev, bool dereset)
dsaf_write_sub(dsaf_dev, nt_reg_addr, RESET_REQ_OR_DREQ);
}
+static void hns_dsaf_rst_acpi(struct dsaf_device *dsaf_dev, bool dereset)
+{
+ hns_dsaf_acpi_srst_by_port(dsaf_dev, HNS_OP_RESET_FUNC,
+ HNS_DSAF_RESET_FUNC,
+ 0, dereset);
+}
+
static void hns_dsaf_xge_srst_by_port(struct dsaf_device *dsaf_dev, u32 port,
bool dereset)
{
@@ -146,6 +202,13 @@ static void hns_dsaf_xge_srst_by_port(struct dsaf_device *dsaf_dev, u32 port,
dsaf_write_sub(dsaf_dev, reg_addr, reg_val);
}
+static void hns_dsaf_xge_srst_by_port_acpi(struct dsaf_device *dsaf_dev,
+ u32 port, bool dereset)
+{
+ hns_dsaf_acpi_srst_by_port(dsaf_dev, HNS_OP_RESET_FUNC,
+ HNS_XGE_RESET_FUNC, port, dereset);
+}
+
static void hns_dsaf_xge_core_srst_by_port(struct dsaf_device *dsaf_dev,
u32 port, bool dereset)
{
@@ -166,6 +229,14 @@ static void hns_dsaf_xge_core_srst_by_port(struct dsaf_device *dsaf_dev,
dsaf_write_sub(dsaf_dev, reg_addr, reg_val);
}
+static void
+hns_dsaf_xge_core_srst_by_port_acpi(struct dsaf_device *dsaf_dev,
+ u32 port, bool dereset)
+{
+ hns_dsaf_acpi_srst_by_port(dsaf_dev, HNS_OP_RESET_FUNC,
+ HNS_XGE_CORE_RESET_FUNC, port, dereset);
+}
+
static void hns_dsaf_ge_srst_by_port(struct dsaf_device *dsaf_dev, u32 port,
bool dereset)
{
@@ -218,6 +289,13 @@ static void hns_dsaf_ge_srst_by_port(struct dsaf_device *dsaf_dev, u32 port,
}
}
+static void hns_dsaf_ge_srst_by_port_acpi(struct dsaf_device *dsaf_dev,
+ u32 port, bool dereset)
+{
+ hns_dsaf_acpi_srst_by_port(dsaf_dev, HNS_OP_RESET_FUNC,
+ HNS_GE_RESET_FUNC, port, dereset);
+}
+
static void hns_ppe_srst_by_port(struct dsaf_device *dsaf_dev, u32 port,
bool dereset)
{
@@ -234,11 +312,21 @@ static void hns_ppe_srst_by_port(struct dsaf_device *dsaf_dev, u32 port,
dsaf_write_sub(dsaf_dev, reg_addr, reg_val);
}
+static void
+hns_ppe_srst_by_port_acpi(struct dsaf_device *dsaf_dev, u32 port, bool dereset)
+{
+ hns_dsaf_acpi_srst_by_port(dsaf_dev, HNS_OP_RESET_FUNC,
+ HNS_PPE_RESET_FUNC, port, dereset);
+}
+
static void hns_ppe_com_srst(struct dsaf_device *dsaf_dev, bool dereset)
{
u32 reg_val;
u32 reg_addr;
+ if (!(dev_of_node(dsaf_dev->dev)))
+ return;
+
if (!HNS_DSAF_IS_DEBUG(dsaf_dev)) {
reg_val = RESET_REQ_OR_DREQ;
if (!dereset)
@@ -295,6 +383,40 @@ static phy_interface_t hns_mac_get_phy_if(struct hns_mac_cb *mac_cb)
return phy_if;
}
+static phy_interface_t hns_mac_get_phy_if_acpi(struct hns_mac_cb *mac_cb)
+{
+ phy_interface_t phy_if = PHY_INTERFACE_MODE_NA;
+ union acpi_object *obj;
+ union acpi_object obj_args, argv4;
+
+ obj_args.integer.type = ACPI_TYPE_INTEGER;
+ obj_args.integer.value = mac_cb->mac_id;
+
+ argv4.type = ACPI_TYPE_PACKAGE,
+ argv4.package.count = 1,
+ argv4.package.elements = &obj_args,
+
+ obj = acpi_evaluate_dsm(ACPI_HANDLE(mac_cb->dev),
+ hns_dsaf_acpi_dsm_uuid, 0,
+ HNS_OP_GET_PORT_TYPE_FUNC, &argv4);
+
+ if (!obj)
+ return phy_if;
+
+ if (obj->type != ACPI_TYPE_INTEGER)
+ goto exit_free;
+
+ phy_if = obj->integer.value ?
+ PHY_INTERFACE_MODE_XGMII : PHY_INTERFACE_MODE_SGMII;
+
+ dev_dbg(mac_cb->dev, "mac_id=%d, phy_if=%d\n", mac_cb->mac_id, phy_if);
+
+exit_free:
+ ACPI_FREE(obj);
+
+ return phy_if;
+}
+
int hns_mac_get_sfp_prsnt(struct hns_mac_cb *mac_cb, int *sfp_prsnt)
{
if (!mac_cb->cpld_ctrl)
@@ -354,6 +476,36 @@ static int hns_mac_config_sds_loopback(struct hns_mac_cb *mac_cb, bool en)
return 0;
}
+static int
+hns_mac_config_sds_loopback_acpi(struct hns_mac_cb *mac_cb, bool en)
+{
+ union acpi_object *obj;
+ union acpi_object obj_args[3], argv4;
+
+ obj_args[0].integer.type = ACPI_TYPE_INTEGER;
+ obj_args[0].integer.value = mac_cb->mac_id;
+ obj_args[1].integer.type = ACPI_TYPE_INTEGER;
+ obj_args[1].integer.value = !!en;
+
+ argv4.type = ACPI_TYPE_PACKAGE;
+ argv4.package.count = 2;
+ argv4.package.elements = obj_args;
+
+ obj = acpi_evaluate_dsm(ACPI_HANDLE(mac_cb->dsaf_dev->dev),
+ hns_dsaf_acpi_dsm_uuid, 0,
+ HNS_OP_SERDES_LP_FUNC, &argv4);
+ if (!obj) {
+ dev_warn(mac_cb->dsaf_dev->dev, "set port%d serdes lp fail!",
+ mac_cb->mac_id);
+
+ return -ENOTSUPP;
+ }
+
+ ACPI_FREE(obj);
+
+ return 0;
+}
+
struct dsaf_misc_op *hns_misc_op_get(struct dsaf_device *dsaf_dev)
{
struct dsaf_misc_op *misc_op;
@@ -378,6 +530,25 @@ struct dsaf_misc_op *hns_misc_op_get(struct dsaf_device *dsaf_dev)
misc_op->get_sfp_prsnt = hns_mac_get_sfp_prsnt;
misc_op->cfg_serdes_loopback = hns_mac_config_sds_loopback;
+ } else if (is_acpi_node(dsaf_dev->dev->fwnode)) {
+ misc_op->cpld_set_led = hns_cpld_set_led;
+ misc_op->cpld_reset_led = cpld_led_reset;
+ misc_op->cpld_set_led_id = cpld_set_led_id;
+
+ misc_op->dsaf_reset = hns_dsaf_rst_acpi;
+ misc_op->xge_srst = hns_dsaf_xge_srst_by_port_acpi;
+ misc_op->xge_core_srst = hns_dsaf_xge_core_srst_by_port_acpi;
+ misc_op->ge_srst = hns_dsaf_ge_srst_by_port_acpi;
+ misc_op->ppe_srst = hns_ppe_srst_by_port_acpi;
+ misc_op->ppe_comm_srst = hns_ppe_com_srst;
+
+ misc_op->get_phy_if = hns_mac_get_phy_if_acpi;
+ misc_op->get_sfp_prsnt = hns_mac_get_sfp_prsnt;
+
+ misc_op->cfg_serdes_loopback = hns_mac_config_sds_loopback_acpi;
+ } else {
+ devm_kfree(dsaf_dev->dev, (void *)misc_op);
+ misc_op = NULL;
}
return (void *)misc_op;
--
1.9.1
[toc] | [prev] | [next] | [standalone]
| From | Yisen Zhuang <Yisen.Zhuang@huawei.com> |
|---|---|
| Date | 2016-05-30 14:30 +0200 |
| Subject | [PATCH v3 net-next 04/13] net: hisilicon: add support of acpi for hns-mdio |
| Message-ID | <rEuut-47w-13@gated-at.bofh.it> |
| In reply to | #1409050 |
From: Kejian Yan <yankejian@huawei.com>
hns-mdio needs to register itself to mii-bus. The info of the device can
be read by both DT and ACPI.
HNS tries to call Linux PHY driver to help access PHY-devices, the HNS
hardware topology is as below. The MDIO controller may control several
PHY-devices, and each PHY-device connects to a MAC device. The MDIO will
be registered to mdiobus, then PHY-devices will register when each mac
find PHY device.
cpu
|
|
-------------------------------------------
| | |
| | |
| dsaf |
MDIO | MDIO
| --------------------------- |
| | | | | |
| | | | | |
| MAC MAC MAC MAC |
| | | | | |
---- |-------- |-------- | | --------
|| || || ||
PHY PHY PHY PHY
And the driver can handle reset sequence by _RST method in DSDT in ACPI
case.
Signed-off-by: Kejian Yan <yankejian@huawei.com>
Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Signed-off-by: Yisen Zhuang <Yisen.Zhuang@huawei.com>
---
change log:
v3:
add Reviewed-by: Andy Shevchenko
v2:
1. use dev_of_node instead of IS_ENABLED macro
2. Add ACPI bits
Link: https://lkml.org/lkml/2016/5/29/185
v1: first submit
Link: https://lkml.org/lkml/2016/5/13/93
---
drivers/net/ethernet/hisilicon/hns_mdio.c | 107 +++++++++++++++++++-----------
1 file changed, 69 insertions(+), 38 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns_mdio.c b/drivers/net/ethernet/hisilicon/hns_mdio.c
index 381cf0a..f78286c 100644
--- a/drivers/net/ethernet/hisilicon/hns_mdio.c
+++ b/drivers/net/ethernet/hisilicon/hns_mdio.c
@@ -7,6 +7,7 @@
* (at your option) any later version.
*/
+#include <linux/acpi.h>
#include <linux/errno.h>
#include <linux/etherdevice.h>
#include <linux/init.h>
@@ -354,48 +355,60 @@ static int hns_mdio_reset(struct mii_bus *bus)
struct hns_mdio_device *mdio_dev = (struct hns_mdio_device *)bus->priv;
int ret;
- if (!dev_of_node(bus->parent))
- return -ENOTSUPP;
+ if (dev_of_node(bus->parent)) {
+ if (!mdio_dev->subctrl_vbase) {
+ dev_err(&bus->dev, "mdio sys ctl reg has not maped\n");
+ return -ENODEV;
+ }
- if (!mdio_dev->subctrl_vbase) {
- dev_err(&bus->dev, "mdio sys ctl reg has not maped\n");
- return -ENODEV;
- }
+ /* 1. reset req, and read reset st check */
+ ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_RESET_REQ, 0x1,
+ MDIO_SC_RESET_ST, 0x1,
+ MDIO_CHECK_SET_ST);
+ if (ret) {
+ dev_err(&bus->dev, "MDIO reset fail\n");
+ return ret;
+ }
- /*1. reset req, and read reset st check*/
- ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_RESET_REQ, 0x1,
- MDIO_SC_RESET_ST, 0x1,
- MDIO_CHECK_SET_ST);
- if (ret) {
- dev_err(&bus->dev, "MDIO reset fail\n");
- return ret;
- }
+ /* 2. dis clk, and read clk st check */
+ ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_CLK_DIS,
+ 0x1, MDIO_SC_CLK_ST, 0x1,
+ MDIO_CHECK_CLR_ST);
+ if (ret) {
+ dev_err(&bus->dev, "MDIO dis clk fail\n");
+ return ret;
+ }
- /*2. dis clk, and read clk st check*/
- ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_CLK_DIS,
- 0x1, MDIO_SC_CLK_ST, 0x1,
- MDIO_CHECK_CLR_ST);
- if (ret) {
- dev_err(&bus->dev, "MDIO dis clk fail\n");
- return ret;
- }
+ /* 3. reset dreq, and read reset st check */
+ ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_RESET_DREQ, 0x1,
+ MDIO_SC_RESET_ST, 0x1,
+ MDIO_CHECK_CLR_ST);
+ if (ret) {
+ dev_err(&bus->dev, "MDIO dis clk fail\n");
+ return ret;
+ }
- /*3. reset dreq, and read reset st check*/
- ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_RESET_DREQ, 0x1,
- MDIO_SC_RESET_ST, 0x1,
- MDIO_CHECK_CLR_ST);
- if (ret) {
- dev_err(&bus->dev, "MDIO dis clk fail\n");
- return ret;
+ /* 4. en clk, and read clk st check */
+ ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_CLK_EN,
+ 0x1, MDIO_SC_CLK_ST, 0x1,
+ MDIO_CHECK_SET_ST);
+ if (ret)
+ dev_err(&bus->dev, "MDIO en clk fail\n");
+ } else if (is_acpi_node(bus->parent->fwnode)) {
+ acpi_status s;
+
+ s = acpi_evaluate_object(ACPI_HANDLE(bus->parent),
+ "_RST", NULL, NULL);
+ if (ACPI_FAILURE(s)) {
+ dev_err(&bus->dev, "Reset failed, return:%#x\n", s);
+ ret = -EBUSY;
+ } else {
+ ret = 0;
+ }
+ } else {
+ dev_err(&bus->dev, "Can not get cfg data from DT or ACPI\n");
+ ret = -ENXIO;
}
-
- /*4. en clk, and read clk st check*/
- ret = mdio_sc_cfg_reg_write(mdio_dev, MDIO_SC_CLK_EN,
- 0x1, MDIO_SC_CLK_ST, 0x1,
- MDIO_CHECK_SET_ST);
- if (ret)
- dev_err(&bus->dev, "MDIO en clk fail\n");
-
return ret;
}
@@ -453,7 +466,6 @@ static int hns_mdio_probe(struct platform_device *pdev)
}
platform_set_drvdata(pdev, new_bus);
-
hns_mdio_bus_name(new_bus->id, res->start);
if (dev_of_node(&pdev->dev)) {
mdio_dev->subctrl_vbase = syscon_node_to_regmap(
@@ -464,6 +476,18 @@ static int hns_mdio_probe(struct platform_device *pdev)
mdio_dev->subctrl_vbase = NULL;
}
ret = of_mdiobus_register(new_bus, pdev->dev.of_node);
+ } else if (is_acpi_node(pdev->dev.fwnode)) {
+ /* Clear all the IRQ properties */
+ memset(new_bus->irq, PHY_POLL, 4 * PHY_MAX_ADDR);
+
+ /* Mask out all PHYs from auto probing. */
+ new_bus->phy_mask = ~0;
+
+ /* Register the MDIO bus */
+ ret = mdiobus_register(new_bus);
+ } else {
+ dev_err(&pdev->dev, "Can not get cfg data from DT or ACPI\n");
+ ret = -ENXIO;
}
if (ret) {
@@ -499,12 +523,19 @@ static const struct of_device_id hns_mdio_match[] = {
{}
};
+static const struct acpi_device_id hns_mdio_acpi_match[] = {
+ { "HISI0141", 0 },
+ { },
+};
+MODULE_DEVICE_TABLE(acpi, hns_mdio_acpi_match);
+
static struct platform_driver hns_mdio_driver = {
.probe = hns_mdio_probe,
.remove = hns_mdio_remove,
.driver = {
.name = MDIO_DRV_NAME,
.of_match_table = hns_mdio_match,
+ .acpi_match_table = ACPI_PTR(hns_mdio_acpi_match),
},
};
--
1.9.1
[toc] | [prev] | [next] | [standalone]
| From | Yisen Zhuang <Yisen.Zhuang@huawei.com> |
|---|---|
| Date | 2016-05-30 14:30 +0200 |
| Subject | [PATCH v3 net-next 08/13] net: hns: add uniform interface for phy connection |
| Message-ID | <rEuut-47w-9@gated-at.bofh.it> |
| In reply to | #1409050 |
From: Kejian Yan <yankejian@huawei.com>
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: Kejian Yan <yankejian@huawei.com>
Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Signed-off-by: Yisen Zhuang <Yisen.Zhuang@huawei.com>
---
change log:
v3:
add Reviewed-by: Andy Shevchenko
v2:
1. remove the redundant functions, and
2. adds fwnode match method beside DT and ACPI.
link: https://lkml.org/lkml/2016/5/29/175
v1: first submit
link: https://lkml.org/lkml/2016/5/13/100
---
drivers/net/ethernet/hisilicon/hns/hnae.c | 8 ++++-
drivers/net/ethernet/hisilicon/hns/hnae.h | 3 +-
drivers/net/ethernet/hisilicon/hns/hns_ae_adapt.c | 2 +-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.c | 34 +++++++++++++++-------
drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.h | 2 +-
drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c | 2 +-
drivers/net/ethernet/hisilicon/hns/hns_enet.c | 21 +++++++------
drivers/net/ethernet/hisilicon/hns/hns_ethtool.c | 2 +-
8 files changed, 49 insertions(+), 25 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns/hnae.c b/drivers/net/ethernet/hisilicon/hns/hnae.c
index d630acd..5d3047c 100644
--- a/drivers/net/ethernet/hisilicon/hns/hnae.c
+++ b/drivers/net/ethernet/hisilicon/hns/hnae.c
@@ -96,7 +96,13 @@ static int __ae_match(struct device *dev, const void *data)
{
struct hnae_ae_dev *hdev = cls_to_ae_dev(dev);
- return (data == &hdev->dev->of_node->fwnode);
+ 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)
diff --git a/drivers/net/ethernet/hisilicon/hns/hnae.h b/drivers/net/ethernet/hisilicon/hns/hnae.h
index f5f8140..529cb13 100644
--- a/drivers/net/ethernet/hisilicon/hns/hnae.h
+++ b/drivers/net/ethernet/hisilicon/hns/hnae.h
@@ -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;
diff --git a/drivers/net/ethernet/hisilicon/hns/hns_ae_adapt.c b/drivers/net/ethernet/hisilicon/hns/hns_ae_adapt.c
index 7a757e8..8e009f4 100644
--- a/drivers/net/ethernet/hisilicon/hns/hns_ae_adapt.c
+++ b/drivers/net/ethernet/hisilicon/hns/hns_ae_adapt.c
@@ -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;
diff --git a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.c b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.c
index 611581f..527b49d 100644
--- a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.c
+++ b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.c
@@ -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 @@ free_mac_drv:
*/
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",
- mac_cb->mac_id);
- if (mac_cb->phy_node)
+ np = of_parse_phandle(mac_cb->dev->of_node, "phy-handle",
+ mac_cb->mac_id);
+ 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));
diff --git a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.h b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.h
index 97ce9a7..89b49d7 100644
--- a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.h
+++ b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_mac.h
@@ -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;
};
diff --git a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c
index a837bb9..a843a86 100644
--- a/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c
+++ b/drivers/net/ethernet/hisilicon/hns/hns_dsaf_misc.c
@@ -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
diff --git a/drivers/net/ethernet/hisilicon/hns/hns_enet.c b/drivers/net/ethernet/hisilicon/hns/hns_enet.c
index 93f6ccb..3ec3c27 100644
--- a/drivers/net/ethernet/hisilicon/hns/hns_enet.c
+++ b/drivers/net/ethernet/hisilicon/hns/hns_enet.c
@@ -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;
diff --git a/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c b/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c
index 3d746c8..03007d2 100644
--- a/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c
+++ b/drivers/net/ethernet/hisilicon/hns/hns_ethtool.c
@@ -597,7 +597,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) {
--
1.9.1
[toc] | [prev] | [standalone]
Back to top | Article view | linux.kernel
csiph-web