From: Maxime Chevallier <maxime.chevallier@bootlin.com>
To: Vivian Wang <wangruikang@iscas.ac.cn>
Cc: Andrew Lunn <andrew+netdev@lunn.ch>,
"David S. Miller" <davem@davemloft.net>,
Eric Dumazet <edumazet@google.com>,
Jakub Kicinski <kuba@kernel.org>, Paolo Abeni <pabeni@redhat.com>,
Rob Herring <robh@kernel.org>,
Krzysztof Kozlowski <krzk+dt@kernel.org>,
Conor Dooley <conor+dt@kernel.org>, Yixun Lan <dlan@gentoo.org>,
Philipp Zabel <p.zabel@pengutronix.de>,
Paul Walmsley <paul.walmsley@sifive.com>,
Palmer Dabbelt <palmer@dabbelt.com>,
Albert Ou <aou@eecs.berkeley.edu>,
Alexandre Ghiti <alex@ghiti.fr>, Vivian Wang <uwu@dram.page>,
Lukas Bulwahn <lukas.bulwahn@redhat.com>,
Geert Uytterhoeven <geert+renesas@glider.be>,
Parthiban Veerasooran <Parthiban.Veerasooran@microchip.com>,
netdev@vger.kernel.org, devicetree@vger.kernel.org,
linux-riscv@lists.infradead.org, spacemit@lists.linux.dev,
linux-kernel@vger.kernel.org
Subject: Re: [PATCH net-next v3 2/5] net: spacemit: Add K1 Ethernet MAC
Date: Wed, 2 Jul 2025 09:17:08 +0200 [thread overview]
Message-ID: <20250702091708.7d459213@fedora.home> (raw)
In-Reply-To: <20250702-net-k1-emac-v3-2-882dc55404f3@iscas.ac.cn>
Hello Vivian,
On Wed, 02 Jul 2025 14:01:41 +0800
Vivian Wang <wangruikang@iscas.ac.cn> wrote:
> The Ethernet MACs found on SpacemiT K1 appears to be a custom design
> that only superficially resembles some other embedded MACs. SpacemiT
> refers to them as "EMAC", so let's just call the driver "k1_emac".
>
> This driver is based on "k1x-emac" in the same directory in the vendor's
> tree [1]. Some debugging tunables have been fixed to vendor-recommended
> defaults, and PTP support is not included yet.
>
> [1]: https://github.com/spacemit-com/linux-k1x
>
> Signed-off-by: Vivian Wang <wangruikang@iscas.ac.cn>
I have a handful of tiny comments, the rest looks fine by me !
> +static int emac_phy_connect(struct net_device *ndev)
> +{
> + struct emac_priv *priv = netdev_priv(ndev);
> + struct device *dev = &priv->pdev->dev;
> + struct phy_device *phydev;
> + struct device_node *np;
> + int ret;
> +
> + ret = of_get_phy_mode(dev->of_node, &priv->phy_interface);
> + if (ret) {
> + dev_err(dev, "No phy-mode found");
> + return ret;
> + }
> +
> + np = of_parse_phandle(dev->of_node, "phy-handle", 0);
> + if (!np && of_phy_is_fixed_link(dev->of_node))
> + np = of_node_get(dev->of_node);
> +
> + if (!np) {
> + dev_err(dev, "No PHY specified");
> + return -ENODEV;
> + }
> +
> + ret = emac_phy_interface_config(priv);
> + if (ret)
> + goto err_node_put;
> +
> + phydev = of_phy_connect(ndev, np, &emac_adjust_link, 0,
> + priv->phy_interface);
> + if (!phydev) {
> + dev_err(dev, "Could not attach to PHY\n");
> + ret = -ENODEV;
> + goto err_node_put;
> + }
> +
> + phydev->mac_managed_pm = true;
> +
> + ndev->phydev = phydev;
of_phy_connect() eventually calls phy_attach_direct(), which sets
ndev->phydev, so you don't need to do it here :)
> +
> + emac_update_delay_line(priv);
> +
> +err_node_put:
> + of_node_put(np);
> + return ret;
> +}
[ ... ]
> +static int emac_down(struct emac_priv *priv)
> +{
> + struct platform_device *pdev = priv->pdev;
> + struct net_device *ndev = priv->ndev;
> +
> + netif_stop_queue(ndev);
> +
> + phy_stop(ndev->phydev);
phy_disconnect() will call phy_stop() for you, you can remove it.
> + phy_disconnect(ndev->phydev);
> +
> + emac_wr(priv, MAC_INTERRUPT_ENABLE, 0x0);
> + emac_wr(priv, DMA_INTERRUPT_ENABLE, 0x0);
> +
> + free_irq(priv->irq, ndev);
> +
> + napi_disable(&priv->napi);
> +
> + emac_reset_hw(priv);
> +
> + pm_runtime_put_sync(&pdev->dev);
> + return 0;
> +}
> +
[ ... ]
> +static int emac_probe(struct platform_device *pdev)
> +{
> + struct device *dev = &pdev->dev;
> + struct reset_control *reset;
> + struct net_device *ndev;
> + struct emac_priv *priv;
> + int ret;
> +
> + ndev = devm_alloc_etherdev(dev, sizeof(struct emac_priv));
> + if (!ndev)
> + return -ENOMEM;
> +
> + ndev->hw_features = NETIF_F_SG;
> + ndev->features |= ndev->hw_features;
> +
> + ndev->min_mtu = ETH_MIN_MTU;
This should already be the default value when using
devm_alloc_etherdev()
> + ndev->max_mtu = EMAC_RX_BUF_4K - (ETH_HLEN + ETH_FCS_LEN);
> +
> + priv = netdev_priv(ndev);
> + priv->ndev = ndev;
> + priv->pdev = pdev;
> + platform_set_drvdata(pdev, priv);
> + priv->hw_stats = devm_kzalloc(dev, sizeof(*priv->hw_stats), GFP_KERNEL);
> + if (!priv->hw_stats) {
> + dev_err(dev, "Failed to allocate memory for stats\n");
> + ret = -ENOMEM;
> + goto err;
> + }
> +
> + ret = emac_config_dt(pdev, priv);
> + if (ret < 0) {
> + dev_err(dev, "Configuration failed\n");
> + goto err;
> + }
> +
> + ndev->watchdog_timeo = 5 * HZ;
> + ndev->base_addr = (unsigned long)priv->iobase;
> + ndev->irq = priv->irq;
> +
> + ndev->ethtool_ops = &emac_ethtool_ops;
> + ndev->netdev_ops = &emac_netdev_ops;
> +
> + devm_pm_runtime_enable(&pdev->dev);
> +
> + priv->bus_clk = devm_clk_get_enabled(&pdev->dev, NULL);
> + if (IS_ERR(priv->bus_clk)) {
> + ret = dev_err_probe(dev, PTR_ERR(priv->bus_clk),
> + "Failed to get clock\n");
> + goto err;
> + }
> +
> + reset = devm_reset_control_get_optional_exclusive_deasserted(&pdev->dev,
> + NULL);
> + if (IS_ERR(reset)) {
> + ret = dev_err_probe(dev, PTR_ERR(reset),
> + "Failed to get reset\n");
> + goto err;
> + }
> +
> + emac_sw_init(priv);
> +
> + if (of_phy_is_fixed_link(dev->of_node)) {
> + ret = of_phy_register_fixed_link(dev->of_node);
> + if (ret) {
> + dev_err_probe(dev, ret,
> + "Failed to register fixed-link");
> + goto err_timer_delete;
> + }
It looks like you're missing the calls to:
of_phy_deregister_fixed_link()
in the error path here as well as in the .remove() function.
> + }
> +
> + ret = emac_mdio_init(priv);
> + if (ret)
> + goto err_timer_delete;
> +
> + SET_NETDEV_DEV(ndev, &pdev->dev);
> +
> + ret = devm_register_netdev(dev, ndev);
> + if (ret) {
> + dev_err(dev, "devm_register_netdev failed\n");
> + goto err_timer_delete;
> + }
> +
> + netif_napi_add(ndev, &priv->napi, emac_rx_poll);
> + netif_carrier_off(ndev);
> +
> + return 0;
> +
> +err_timer_delete:
> + timer_delete_sync(&priv->txtimer);
> +err:
> + return ret;
> +}
Maxime
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv
WARNING: multiple messages have this Message-ID (diff)
From: Maxime Chevallier <maxime.chevallier@bootlin.com>
To: Vivian Wang <wangruikang@iscas.ac.cn>
Cc: Andrew Lunn <andrew+netdev@lunn.ch>,
"David S. Miller" <davem@davemloft.net>,
Eric Dumazet <edumazet@google.com>,
Jakub Kicinski <kuba@kernel.org>, Paolo Abeni <pabeni@redhat.com>,
Rob Herring <robh@kernel.org>,
Krzysztof Kozlowski <krzk+dt@kernel.org>,
Conor Dooley <conor+dt@kernel.org>, Yixun Lan <dlan@gentoo.org>,
Philipp Zabel <p.zabel@pengutronix.de>,
Paul Walmsley <paul.walmsley@sifive.com>,
Palmer Dabbelt <palmer@dabbelt.com>,
Albert Ou <aou@eecs.berkeley.edu>,
Alexandre Ghiti <alex@ghiti.fr>, Vivian Wang <uwu@dram.page>,
Lukas Bulwahn <lukas.bulwahn@redhat.com>,
Geert Uytterhoeven <geert+renesas@glider.be>,
Parthiban Veerasooran <Parthiban.Veerasooran@microchip.com>,
netdev@vger.kernel.org, devicetree@vger.kernel.org,
linux-riscv@lists.infradead.org, spacemit@lists.linux.dev,
linux-kernel@vger.kernel.org
Subject: Re: [PATCH net-next v3 2/5] net: spacemit: Add K1 Ethernet MAC
Date: Wed, 2 Jul 2025 09:17:08 +0200 [thread overview]
Message-ID: <20250702091708.7d459213@fedora.home> (raw)
In-Reply-To: <20250702-net-k1-emac-v3-2-882dc55404f3@iscas.ac.cn>
Hello Vivian,
On Wed, 02 Jul 2025 14:01:41 +0800
Vivian Wang <wangruikang@iscas.ac.cn> wrote:
> The Ethernet MACs found on SpacemiT K1 appears to be a custom design
> that only superficially resembles some other embedded MACs. SpacemiT
> refers to them as "EMAC", so let's just call the driver "k1_emac".
>
> This driver is based on "k1x-emac" in the same directory in the vendor's
> tree [1]. Some debugging tunables have been fixed to vendor-recommended
> defaults, and PTP support is not included yet.
>
> [1]: https://github.com/spacemit-com/linux-k1x
>
> Signed-off-by: Vivian Wang <wangruikang@iscas.ac.cn>
I have a handful of tiny comments, the rest looks fine by me !
> +static int emac_phy_connect(struct net_device *ndev)
> +{
> + struct emac_priv *priv = netdev_priv(ndev);
> + struct device *dev = &priv->pdev->dev;
> + struct phy_device *phydev;
> + struct device_node *np;
> + int ret;
> +
> + ret = of_get_phy_mode(dev->of_node, &priv->phy_interface);
> + if (ret) {
> + dev_err(dev, "No phy-mode found");
> + return ret;
> + }
> +
> + np = of_parse_phandle(dev->of_node, "phy-handle", 0);
> + if (!np && of_phy_is_fixed_link(dev->of_node))
> + np = of_node_get(dev->of_node);
> +
> + if (!np) {
> + dev_err(dev, "No PHY specified");
> + return -ENODEV;
> + }
> +
> + ret = emac_phy_interface_config(priv);
> + if (ret)
> + goto err_node_put;
> +
> + phydev = of_phy_connect(ndev, np, &emac_adjust_link, 0,
> + priv->phy_interface);
> + if (!phydev) {
> + dev_err(dev, "Could not attach to PHY\n");
> + ret = -ENODEV;
> + goto err_node_put;
> + }
> +
> + phydev->mac_managed_pm = true;
> +
> + ndev->phydev = phydev;
of_phy_connect() eventually calls phy_attach_direct(), which sets
ndev->phydev, so you don't need to do it here :)
> +
> + emac_update_delay_line(priv);
> +
> +err_node_put:
> + of_node_put(np);
> + return ret;
> +}
[ ... ]
> +static int emac_down(struct emac_priv *priv)
> +{
> + struct platform_device *pdev = priv->pdev;
> + struct net_device *ndev = priv->ndev;
> +
> + netif_stop_queue(ndev);
> +
> + phy_stop(ndev->phydev);
phy_disconnect() will call phy_stop() for you, you can remove it.
> + phy_disconnect(ndev->phydev);
> +
> + emac_wr(priv, MAC_INTERRUPT_ENABLE, 0x0);
> + emac_wr(priv, DMA_INTERRUPT_ENABLE, 0x0);
> +
> + free_irq(priv->irq, ndev);
> +
> + napi_disable(&priv->napi);
> +
> + emac_reset_hw(priv);
> +
> + pm_runtime_put_sync(&pdev->dev);
> + return 0;
> +}
> +
[ ... ]
> +static int emac_probe(struct platform_device *pdev)
> +{
> + struct device *dev = &pdev->dev;
> + struct reset_control *reset;
> + struct net_device *ndev;
> + struct emac_priv *priv;
> + int ret;
> +
> + ndev = devm_alloc_etherdev(dev, sizeof(struct emac_priv));
> + if (!ndev)
> + return -ENOMEM;
> +
> + ndev->hw_features = NETIF_F_SG;
> + ndev->features |= ndev->hw_features;
> +
> + ndev->min_mtu = ETH_MIN_MTU;
This should already be the default value when using
devm_alloc_etherdev()
> + ndev->max_mtu = EMAC_RX_BUF_4K - (ETH_HLEN + ETH_FCS_LEN);
> +
> + priv = netdev_priv(ndev);
> + priv->ndev = ndev;
> + priv->pdev = pdev;
> + platform_set_drvdata(pdev, priv);
> + priv->hw_stats = devm_kzalloc(dev, sizeof(*priv->hw_stats), GFP_KERNEL);
> + if (!priv->hw_stats) {
> + dev_err(dev, "Failed to allocate memory for stats\n");
> + ret = -ENOMEM;
> + goto err;
> + }
> +
> + ret = emac_config_dt(pdev, priv);
> + if (ret < 0) {
> + dev_err(dev, "Configuration failed\n");
> + goto err;
> + }
> +
> + ndev->watchdog_timeo = 5 * HZ;
> + ndev->base_addr = (unsigned long)priv->iobase;
> + ndev->irq = priv->irq;
> +
> + ndev->ethtool_ops = &emac_ethtool_ops;
> + ndev->netdev_ops = &emac_netdev_ops;
> +
> + devm_pm_runtime_enable(&pdev->dev);
> +
> + priv->bus_clk = devm_clk_get_enabled(&pdev->dev, NULL);
> + if (IS_ERR(priv->bus_clk)) {
> + ret = dev_err_probe(dev, PTR_ERR(priv->bus_clk),
> + "Failed to get clock\n");
> + goto err;
> + }
> +
> + reset = devm_reset_control_get_optional_exclusive_deasserted(&pdev->dev,
> + NULL);
> + if (IS_ERR(reset)) {
> + ret = dev_err_probe(dev, PTR_ERR(reset),
> + "Failed to get reset\n");
> + goto err;
> + }
> +
> + emac_sw_init(priv);
> +
> + if (of_phy_is_fixed_link(dev->of_node)) {
> + ret = of_phy_register_fixed_link(dev->of_node);
> + if (ret) {
> + dev_err_probe(dev, ret,
> + "Failed to register fixed-link");
> + goto err_timer_delete;
> + }
It looks like you're missing the calls to:
of_phy_deregister_fixed_link()
in the error path here as well as in the .remove() function.
> + }
> +
> + ret = emac_mdio_init(priv);
> + if (ret)
> + goto err_timer_delete;
> +
> + SET_NETDEV_DEV(ndev, &pdev->dev);
> +
> + ret = devm_register_netdev(dev, ndev);
> + if (ret) {
> + dev_err(dev, "devm_register_netdev failed\n");
> + goto err_timer_delete;
> + }
> +
> + netif_napi_add(ndev, &priv->napi, emac_rx_poll);
> + netif_carrier_off(ndev);
> +
> + return 0;
> +
> +err_timer_delete:
> + timer_delete_sync(&priv->txtimer);
> +err:
> + return ret;
> +}
Maxime
next prev parent reply other threads:[~2025-07-02 7:17 UTC|newest]
Thread overview: 30+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-07-02 6:01 [PATCH net-next v3 0/5] Add Ethernet MAC support for SpacemiT K1 Vivian Wang
2025-07-02 6:01 ` Vivian Wang
2025-07-02 6:01 ` [PATCH net-next v3 1/5] dt-bindings: net: Add " Vivian Wang
2025-07-02 6:01 ` Vivian Wang
2025-07-02 6:01 ` [PATCH net-next v3 2/5] net: spacemit: Add K1 Ethernet MAC Vivian Wang
2025-07-02 6:01 ` Vivian Wang
2025-07-02 7:17 ` Maxime Chevallier [this message]
2025-07-02 7:17 ` Maxime Chevallier
2025-07-02 7:41 ` Vivian Wang
2025-07-02 7:41 ` Vivian Wang
2025-07-03 7:19 ` Simon Horman
2025-07-03 7:19 ` Simon Horman
2025-07-03 7:58 ` Vivian Wang
2025-07-03 7:58 ` Vivian Wang
2025-07-02 6:01 ` [PATCH net-next v3 3/5] riscv: dts: spacemit: Add Ethernet support for K1 Vivian Wang
2025-07-02 6:01 ` Vivian Wang
2025-07-02 6:01 ` [PATCH net-next v3 4/5] riscv: dts: spacemit: Add Ethernet support for BPI-F3 Vivian Wang
2025-07-02 6:01 ` Vivian Wang
2025-07-02 6:01 ` [PATCH net-next v3 5/5] riscv: dts: spacemit: Add Ethernet support for Jupiter Vivian Wang
2025-07-02 6:01 ` Vivian Wang
2025-07-03 6:48 ` Junhui Liu
2025-07-03 6:48 ` Junhui Liu
2025-07-03 7:46 ` Vivian Wang
2025-07-03 7:46 ` Vivian Wang
2025-07-03 9:00 ` Junhui Liu
2025-07-03 9:00 ` Junhui Liu
2025-07-03 7:23 ` [PATCH net-next v3 0/5] Add Ethernet MAC support for SpacemiT K1 Simon Horman
2025-07-03 7:23 ` Simon Horman
2025-07-03 7:39 ` Vivian Wang
2025-07-03 7:39 ` Vivian Wang
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20250702091708.7d459213@fedora.home \
--to=maxime.chevallier@bootlin.com \
--cc=Parthiban.Veerasooran@microchip.com \
--cc=alex@ghiti.fr \
--cc=andrew+netdev@lunn.ch \
--cc=aou@eecs.berkeley.edu \
--cc=conor+dt@kernel.org \
--cc=davem@davemloft.net \
--cc=devicetree@vger.kernel.org \
--cc=dlan@gentoo.org \
--cc=edumazet@google.com \
--cc=geert+renesas@glider.be \
--cc=krzk+dt@kernel.org \
--cc=kuba@kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-riscv@lists.infradead.org \
--cc=lukas.bulwahn@redhat.com \
--cc=netdev@vger.kernel.org \
--cc=p.zabel@pengutronix.de \
--cc=pabeni@redhat.com \
--cc=palmer@dabbelt.com \
--cc=paul.walmsley@sifive.com \
--cc=robh@kernel.org \
--cc=spacemit@lists.linux.dev \
--cc=uwu@dram.page \
--cc=wangruikang@iscas.ac.cn \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.