From patchwork Wed Nov 30 17:42:44 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710623 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=85.214.62.61; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384) server-digest SHA384) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMml15974z23nT for ; Thu, 1 Dec 2022 04:43:09 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id AF41D853C8; Wed, 30 Nov 2022 18:43:03 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id 3519F853C2; Wed, 30 Nov 2022 18:43:01 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id BF5C880A55 for ; Wed, 30 Nov 2022 18:42:58 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6l-0016xU-53; Wed, 30 Nov 2022 17:42:55 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 1/8] net: mdio-uclass: scan for dm mdio children on post-bind Date: Wed, 30 Nov 2022 09:42:44 -0800 Message-Id: <20221130174251.82087-2-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean If a DM_MDIO driver is used we need to scan the subnodes as well. Signed-off-by: Tim Harvey Signed-off-by: Vladimir Oltean Reviewed-by: Ramon Fried Reviewed-by: Fabio Estevam --- v9: - no changes v8: - no changes v7: - no changes v6: - no changes v5: - added Fabio's rb tag v4: - no changes v3: - no changes v2: - added Ramon's rb tag --- net/mdio-uclass.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/net/mdio-uclass.c b/net/mdio-uclass.c index 4401492ca015..d80037d0ac71 100644 --- a/net/mdio-uclass.c +++ b/net/mdio-uclass.c @@ -49,7 +49,11 @@ static int dm_mdio_post_bind(struct udevice *dev) return -EINVAL; } +#if CONFIG_IS_ENABLED(OF_REAL) + return dm_scan_fdt_dev(dev); +#else return 0; +#endif } int dm_mdio_read(struct udevice *mdio_dev, int addr, int devad, int reg) From patchwork Wed Nov 30 17:42:45 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710625 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=85.214.62.61; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMmlR3z9kz23nT for ; Thu, 1 Dec 2022 04:43:31 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id C4786830E3; Wed, 30 Nov 2022 18:43:11 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id 8A3F8853CE; Wed, 30 Nov 2022 18:43:04 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 3EBBB84225 for ; Wed, 30 Nov 2022 18:42:59 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6l-0016xU-Tj; Wed, 30 Nov 2022 17:42:56 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 2/8] net: dsa: move cpu port probe to dsa_post_probe Date: Wed, 30 Nov 2022 09:42:45 -0800 Message-Id: <20221130174251.82087-3-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean In order to ensure that a DSA driver probe gets called before dsa_ops->port_probe move the port_probe of the cpu_port to a post-probe function. Signed-off-by: Tim Harvey Reviewed-by: Ramon Fried Reviewed-by: Vladimir Oltean Reviewed-by: Fabio Estevam --- v9: - no changes v8: - no changes v7: - no changes v6: - removed unnecessary semicolon v5: - added Fabio's rb tag v4: - no changes v3: - added Vladimir's rb tag v2: - added Ramon's rb tag --- net/dsa-uclass.c | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/net/dsa-uclass.c b/net/dsa-uclass.c index 5b7046432ff3..5759cedcbec3 100644 --- a/net/dsa-uclass.c +++ b/net/dsa-uclass.c @@ -466,7 +466,6 @@ static int dsa_pre_probe(struct udevice *dev) { struct dsa_pdata *pdata = dev_get_uclass_plat(dev); struct dsa_priv *priv = dev_get_uclass_priv(dev); - struct dsa_ops *ops = dsa_get_ops(dev); int err; priv->num_ports = pdata->num_ports; @@ -482,6 +481,15 @@ static int dsa_pre_probe(struct udevice *dev) if (err) return err; + return 0; +} + +static int dsa_post_probe(struct udevice *dev) +{ + struct dsa_priv *priv = dev_get_uclass_priv(dev); + struct dsa_ops *ops = dsa_get_ops(dev); + int err; + /* Simulate a probing event for the CPU port */ if (ops->port_probe) { err = ops->port_probe(dev, priv->cpu_port, @@ -498,6 +506,7 @@ UCLASS_DRIVER(dsa) = { .name = "dsa", .post_bind = dsa_post_bind, .pre_probe = dsa_pre_probe, + .post_probe = dsa_post_probe, .per_device_auto = sizeof(struct dsa_priv), .per_device_plat_auto = sizeof(struct dsa_pdata), .per_child_plat_auto = sizeof(struct dsa_port_pdata), From patchwork Wed Nov 30 17:42:46 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710627 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=2a01:238:438b:c500:173d:9f52:ddab:ee01; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [IPv6:2a01:238:438b:c500:173d:9f52:ddab:ee01]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMmls3qf3z23nT for ; Thu, 1 Dec 2022 04:43:53 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id 0F756850EE; Wed, 30 Nov 2022 18:43:17 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id BAD6384225; Wed, 30 Nov 2022 18:43:04 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 083C2850EE for ; Wed, 30 Nov 2022 18:43:00 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6m-0016xU-Ls; Wed, 30 Nov 2022 17:42:56 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 3/8] net: dsa: ensure dsa driver has proper ops Date: Wed, 30 Nov 2022 09:42:46 -0800 Message-Id: <20221130174251.82087-4-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean Add a function to sanity check a dsa driver having proper ops. Suggested-by: Vladimir Oltean Signed-off-by: Tim Harvey Reviewed-by: Vladimir Oltean Reviewed-by: Fabio Estevam --- v9: - no changes v8: - no changes v7: - no changes v6: - no changes v5: - added Fabio's rb tag v4: - no changes v3: - added Vladimir's rb tag v2: new patch --- net/dsa-uclass.c | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/net/dsa-uclass.c b/net/dsa-uclass.c index 5759cedcbec3..211a991cdd0d 100644 --- a/net/dsa-uclass.c +++ b/net/dsa-uclass.c @@ -342,6 +342,19 @@ U_BOOT_DRIVER(dsa_port) = { .plat_auto = sizeof(struct eth_pdata), }; +static int dsa_sanitize_ops(struct udevice *dev) +{ + struct dsa_ops *ops = dsa_get_ops(dev); + + if ((!ops->xmit || !ops->rcv) && + (!ops->port_enable && !ops->port_disable)) { + dev_err(dev, "Packets cannot be steered to ports\n"); + return -EINVAL; + } + + return 0; +} + /* * This function mostly deals with pulling information out of the device tree * into the pdata structure. @@ -358,6 +371,10 @@ static int dsa_post_bind(struct udevice *dev) if (!ofnode_valid(node)) return -ENODEV; + err = dsa_sanitize_ops(dev); + if (err) + return err; + pdata->master_node = ofnode_null(); node = ofnode_find_subnode(node, "ports"); From patchwork Wed Nov 30 17:42:47 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710628 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=2a01:238:438b:c500:173d:9f52:ddab:ee01; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [IPv6:2a01:238:438b:c500:173d:9f52:ddab:ee01]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMmm511Gvz23nT for ; Thu, 1 Dec 2022 04:44:05 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id CC072853C5; Wed, 30 Nov 2022 18:43:19 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id 5986E853CE; Wed, 30 Nov 2022 18:43:05 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 36651853B8 for ; Wed, 30 Nov 2022 18:43:00 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6n-0016xU-EU; Wed, 30 Nov 2022 17:42:57 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 4/8] net: dsa: allow rcv() and xmit() to be optional Date: Wed, 30 Nov 2022 09:42:47 -0800 Message-Id: <20221130174251.82087-5-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean Allow rcv() and xmit() dsa driver ops to be optional in case a driver does not care to mangle a packet as in U-Boot only one network port is enabled at a time and thus no packet mangling is necessary. Suggested-by: Vladimir Oltean Signed-off-by: Tim Harvey Reviewed-by: Vladimir Oltean Reviewed-by: Fabio Estevam Signed-off-by: Tim Harvey --- v9: - fixed dsa_port_send when xmit function is defined v8: - no changes v7: - no changes v6: - no changes v5: - added Fabio's rb tag v4: - no changes v3: - added Vladimir's rb tag v2: new patch --- net/dsa-uclass.c | 28 +++++++++++++++------------- 1 file changed, 15 insertions(+), 13 deletions(-) diff --git a/net/dsa-uclass.c b/net/dsa-uclass.c index 211a991cdd0d..dd78e5744d58 100644 --- a/net/dsa-uclass.c +++ b/net/dsa-uclass.c @@ -142,20 +142,22 @@ static int dsa_port_send(struct udevice *pdev, void *packet, int length) struct dsa_port_pdata *port_pdata; int err; - if (length + head + tail > PKTSIZE_ALIGN) - return -EINVAL; + if (ops->xmit) { + if (length + head + tail > PKTSIZE_ALIGN) + return -EINVAL; - memset(dsa_packet_tmp, 0, head); - memset(dsa_packet_tmp + head + length, 0, tail); - memcpy(dsa_packet_tmp + head, packet, length); - length += head + tail; - /* copy back to preserve original buffer alignment */ - memcpy(packet, dsa_packet_tmp, length); + memset(dsa_packet_tmp, 0, head); + memset(dsa_packet_tmp + head + length, 0, tail); + memcpy(dsa_packet_tmp + head, packet, length); + length += head + tail; + /* copy back to preserve original buffer alignment */ + memcpy(packet, dsa_packet_tmp, length); - port_pdata = dev_get_parent_plat(pdev); - err = ops->xmit(dev, port_pdata->index, packet, length); - if (err) - return err; + port_pdata = dev_get_parent_plat(pdev); + err = ops->xmit(dev, port_pdata->index, packet, length); + if (err) + return err; + } return eth_get_ops(master)->send(master, packet, length); } @@ -172,7 +174,7 @@ static int dsa_port_recv(struct udevice *pdev, int flags, uchar **packetp) int length, port_index, err; length = eth_get_ops(master)->recv(master, flags, packetp); - if (length <= 0) + if (length <= 0 || !ops->rcv) return length; /* From patchwork Wed Nov 30 17:42:48 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710626 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=2a01:238:438b:c500:173d:9f52:ddab:ee01; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [IPv6:2a01:238:438b:c500:173d:9f52:ddab:ee01]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMmlf4vPwz23nT for ; Thu, 1 Dec 2022 04:43:42 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id C04AB853C4; Wed, 30 Nov 2022 18:43:14 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id 24F0F84D9F; Wed, 30 Nov 2022 18:43:05 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id E46D7853C1 for ; Wed, 30 Nov 2022 18:43:00 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6o-0016xU-6n; Wed, 30 Nov 2022 17:42:58 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 5/8] net: ksz9477: remove unnecessary xmit and recv functions Date: Wed, 30 Nov 2022 09:42:48 -0800 Message-Id: <20221130174251.82087-6-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean Remove the unnecessary xmit and recv functions. Signed-off-by: Tim Harvey Reviewed-by: Vladimir Oltean Reviewed-by: Fabio Estevam --- v9: - no changes v8: - no changes v7: - no changes v6: - no changes v5: - added Fabio's rb tag v4: - no changes v3: - added Vladimir's rb tag v2: new patch --- drivers/net/ksz9477.c | 23 ----------------------- 1 file changed, 23 deletions(-) diff --git a/drivers/net/ksz9477.c b/drivers/net/ksz9477.c index ed8f1895cb12..fb5c76c600be 100644 --- a/drivers/net/ksz9477.c +++ b/drivers/net/ksz9477.c @@ -62,7 +62,6 @@ struct ksz_dsa_priv { struct udevice *dev; - int active_port; }; static inline int ksz_read8(struct udevice *dev, u32 reg, u8 *val) @@ -382,9 +381,6 @@ static int ksz_port_enable(struct udevice *dev, int port, struct phy_device *phy data8 |= SW_START; ksz_write8(priv->dev, REG_SW_OPERATION, data8); - /* keep track of current enabled non-cpu port */ - priv->active_port = port; - return 0; } @@ -413,28 +409,9 @@ static void ksz_port_disable(struct udevice *dev, int port, struct phy_device *p */ } -static int ksz_xmit(struct udevice *dev, int port, void *packet, int length) -{ - dev_dbg(dev, "%s P%d %d\n", __func__, port + 1, length); - - return 0; -} - -static int ksz_recv(struct udevice *dev, int *port, void *packet, int length) -{ - struct ksz_dsa_priv *priv = dev_get_priv(dev); - - dev_dbg(dev, "%s P%d %d\n", __func__, priv->active_port + 1, length); - *port = priv->active_port; - - return 0; -}; - static const struct dsa_ops ksz_dsa_ops = { .port_enable = ksz_port_enable, .port_disable = ksz_port_disable, - .xmit = ksz_xmit, - .rcv = ksz_recv, }; static int ksz_probe_mdio(struct udevice *dev) From patchwork Wed Nov 30 17:42:49 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710630 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=85.214.62.61; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMmmX4pYLz23nT for ; Thu, 1 Dec 2022 04:44:28 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id 3E09C853D0; Wed, 30 Nov 2022 18:43:25 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id B01CD83A30; Wed, 30 Nov 2022 18:43:08 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 224BB853C3 for ; Wed, 30 Nov 2022 18:43:01 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6o-0016xU-VI; Wed, 30 Nov 2022 17:42:59 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 6/8] net: fec: add support for DM_MDIO Date: Wed, 30 Nov 2022 09:42:49 -0800 Message-Id: <20221130174251.82087-7-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean Add support for DM_MDIO by registering a UCLASS_MDIO driver and attempting to use it. This is necessary if wanting to use a DSA driver for example hanging off of the FEC MAC. Care is taken to fallback to non DM_MDIO mii bus as several boards define DM_MDIO without having the proper device-tree configuration necessary such as an mdio subnode, a phy-mode prop, and either a valid phy-handle prop or fixed-phy subnode which will cause dm_eth_phy_connect() to fail. Signed-off-by: Tim Harvey Reviewed-by: Fabio Estevam --- v9: - no changes v8: - no changes v7: - no changes v6: - no changes v5: - added Fabio's rb tag v4: - no changes v3: - no changes v2: - fix fallback mechanism for legacy dt's that do not have phy-handle and mdio subnode --- drivers/net/fec_mxc.c | 90 ++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 88 insertions(+), 2 deletions(-) diff --git a/drivers/net/fec_mxc.c b/drivers/net/fec_mxc.c index bbc4434ddb9e..7057472710fa 100644 --- a/drivers/net/fec_mxc.c +++ b/drivers/net/fec_mxc.c @@ -30,6 +30,8 @@ #include #include #include +#include +#include #include "fec_mxc.h" #include @@ -1026,6 +1028,81 @@ struct mii_dev *fec_get_miibus(ulong base_addr, int dev_id) return bus; } +#ifdef CONFIG_DM_MDIO +struct dm_fec_mdio_priv { + struct ethernet_regs *regs; +}; + +static int dm_fec_mdio_read(struct udevice *dev, int addr, int devad, int reg) +{ + struct dm_fec_mdio_priv *priv = dev_get_priv(dev); + + return fec_mdio_read(priv->regs, addr, reg); +} + +static int dm_fec_mdio_write(struct udevice *dev, int addr, int devad, int reg, u16 data) +{ + struct dm_fec_mdio_priv *priv = dev_get_priv(dev); + + return fec_mdio_write(priv->regs, addr, reg, data); +} + +static const struct mdio_ops dm_fec_mdio_ops = { + .read = dm_fec_mdio_read, + .write = dm_fec_mdio_write, +}; + +static int dm_fec_mdio_probe(struct udevice *dev) +{ + struct dm_fec_mdio_priv *priv = dev_get_priv(dev); + + priv->regs = (struct ethernet_regs *)ofnode_get_addr(dev_ofnode(dev->parent)); + + return 0; +} + +U_BOOT_DRIVER(fec_mdio) = { + .name = "fec_mdio", + .id = UCLASS_MDIO, + .probe = dm_fec_mdio_probe, + .ops = &dm_fec_mdio_ops, + .priv_auto = sizeof(struct dm_fec_mdio_priv), +}; + +static int dm_fec_bind_mdio(struct udevice *dev) +{ + struct udevice *mdiodev; + const char *name; + ofnode mdio; + int ret = -ENODEV; + + /* for a UCLASS_MDIO driver we need to bind and probe manually + * for an internal MDIO bus that has no dt compatible of its own + */ + ofnode_for_each_subnode(mdio, dev_ofnode(dev)) { + name = ofnode_get_name(mdio); + + if (strcmp(name, "mdio")) + continue; + + ret = device_bind_driver_to_node(dev, "fec_mdio", + name, mdio, &mdiodev); + if (ret) { + printf("%s bind %s failed: %d\n", __func__, name, ret); + break; + } + + /* need to probe it as there is no compatible to do so */ + ret = uclass_get_device_by_ofnode(UCLASS_MDIO, mdio, &mdiodev); + if (!ret) + return 0; + printf("%s probe %s failed: %d\n", __func__, name, ret); + } + + return ret; +} +#endif + static int fecmxc_read_rom_hwaddr(struct udevice *dev) { struct fec_priv *priv = dev_get_priv(dev); @@ -1089,7 +1166,7 @@ static int device_get_phy_addr(struct fec_priv *priv, struct udevice *dev) static int fec_phy_init(struct fec_priv *priv, struct udevice *dev) { - struct phy_device *phydev; + struct phy_device *phydev = NULL; int addr; addr = device_get_phy_addr(priv, dev); @@ -1097,7 +1174,10 @@ static int fec_phy_init(struct fec_priv *priv, struct udevice *dev) addr = CONFIG_FEC_MXC_PHYADDR; #endif - phydev = phy_connect(priv->bus, addr, dev, priv->interface); + if (IS_ENABLED(CONFIG_DM_MDIO)) + phydev = dm_eth_phy_connect(dev); + if (!phydev) + phydev = phy_connect(priv->bus, addr, dev, priv->interface); if (!phydev) return -ENODEV; @@ -1228,6 +1308,12 @@ static int fecmxc_probe(struct udevice *dev) priv->dev_id = dev_seq(dev); + if (IS_ENABLED(CONFIG_DM_MDIO)) { + ret = dm_fec_bind_mdio(dev); + if (ret && ret != -ENODEV) + return ret; + } + #ifdef CONFIG_DM_ETH_PHY bus = eth_phy_get_mdio_bus(dev); #endif From patchwork Wed Nov 30 17:42:50 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710631 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=2a01:238:438b:c500:173d:9f52:ddab:ee01; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [IPv6:2a01:238:438b:c500:173d:9f52:ddab:ee01]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMmml5vCLz23nT for ; Thu, 1 Dec 2022 04:44:39 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id DFECE853E9; Wed, 30 Nov 2022 18:43:36 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id 39E4983A30; Wed, 30 Nov 2022 18:43:11 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 2984580431 for ; Wed, 30 Nov 2022 18:43:02 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6p-0016xU-Nx; Wed, 30 Nov 2022 17:42:59 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 7/8] net: add MV88E6xxx DSA driver Date: Wed, 30 Nov 2022 09:42:50 -0800 Message-Id: <20221130174251.82087-8-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean Add a DSA driver for the MV88E6xxx compatible Ethernet switches. Cc: Marek BehĂșn Cc: Vladimir Oltean Signed-off-by: Tim Harvey Reviewed-by: Vladimir Oltean Reviewed-by: Fabio Estevam --- v9: - no changes v8: - remove energy-detect low-power mode config v7: - rebase on master - update commit short msg (s/MV88E61xx/MV88E6xxx) - replace inline smi_cmd* with macros using logical operators - replace bitfield_replace with logical operators for readibility - removed some unused register definitions - config switch based SERDES mode once in probe vs port_enable - rework port_enable to clean up and: - enable energy-detect for all non fixed PHY ports - configure RGMII delays based on interface type v6: - update commit msg (s/MV88E61xx/MV88E6xxx) - remove GbE from commit msg and Kconfig desc - squash accidental change from patch 7 into patch 6 - added error print on failure to read switch id - mv88e6xxx_probe: - check for switch enabled - remove unused variable enabled - remove unnecessary call to dsa_set_tagging - port_probe: - new function to configure phy features by calling phy_config - port_enable: - only enable energy-detect sensing on phy ports - add phy/cmode verification mistmatch warning - remove mv88e6xxx_fixed_port_setup() - always force link up for fixed ports - always set SERDES mode regardless of cpu port - remove unnecessary setting of CPUDEST - port_disable: - remove pointless error check - removed unnecessary priv data for mdio controller - fix indentation - change variable name for clarity v5: - added support for MV88E6320 - added Fabio's rb tag v4: - rename to mv88e6xxx - sort includes alphabetically - remove dsa term from function names - reduce indentation level and remove unecessary code in of probe_mdio function - rename pdev to mdev to represent mdio device v3: - Added Vladimir's rb tag v2: - rebase on v2022.07-rc1 (use ofnode_get_phy_node) - remove unused commented out fields from struct - remove unused PORT_MASK macro - remove phy from priv struct name - refactor code from original drivers/net/phy/mv88e61xx with suggestions from review to consolidate some functions into mv88e61xx_dsa_port_enable - remove unecessary skiping of disabling of CPU port - remove unecessary dev_set_parent_priv - remove unnecessary static init flag - replace debug with a dev_warn if switch device-id unsupported - remove unnecessary xmit/recv functions as we rely on the fact that only a single port is active instead of mangling packets --- drivers/net/Kconfig | 7 + drivers/net/Makefile | 1 + drivers/net/mv88e6xxx.c | 755 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 763 insertions(+) create mode 100644 drivers/net/mv88e6xxx.c diff --git a/drivers/net/Kconfig b/drivers/net/Kconfig index 029bf3872aa5..88ffd46973da 100644 --- a/drivers/net/Kconfig +++ b/drivers/net/Kconfig @@ -443,6 +443,13 @@ config LITEETH help Driver for the LiteEth Ethernet MAC from LiteX. +config MV88E6XXX + bool "Marvell MV88E6xxx Ethernet switch DSA driver" + depends on DM_DSA && DM_MDIO + help + This driver implements a DSA switch driver for the MV88E6xxx family + of Ethernet switches using the MDIO interface + config MVGBE bool "Marvell Orion5x/Kirkwood network interface support" depends on ARCH_KIRKWOOD || ARCH_ORION5X diff --git a/drivers/net/Makefile b/drivers/net/Makefile index d3fc6b7d3ee4..4088ad0ba5f6 100644 --- a/drivers/net/Makefile +++ b/drivers/net/Makefile @@ -60,6 +60,7 @@ obj-$(CONFIG_MEDIATEK_ETH) += mtk_eth.o obj-$(CONFIG_MPC8XX_FEC) += mpc8xx_fec.o obj-$(CONFIG_MT7620_ETH) += mt7620-eth.o obj-$(CONFIG_MT7628_ETH) += mt7628-eth.o +obj-$(CONFIG_MV88E6XXX) += mv88e6xxx.o obj-$(CONFIG_MVGBE) += mvgbe.o obj-$(CONFIG_MVMDIO) += mvmdio.o obj-$(CONFIG_MVNETA) += mvneta.o diff --git a/drivers/net/mv88e6xxx.c b/drivers/net/mv88e6xxx.c new file mode 100644 index 000000000000..64e860e324dc --- /dev/null +++ b/drivers/net/mv88e6xxx.c @@ -0,0 +1,755 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * (C) Copyright 2022 + * Gateworks Corporation + * Tim Harvey + * + * (C) Copyright 2015 + * Elecsys Corporation + * Kevin Smith + * + * Original driver: + * (C) Copyright 2009 + * Marvell Semiconductor + * Prafulla Wadaskar + */ + +/* + * DSA driver for mv88e6xxx ethernet switches. + * + * This driver configures the mv88e6xxx for basic use as a DSA switch. + * + * This driver was adapted from drivers/net/phy/mv88e61xx and tested + * on the mv88e6176 via an SGMII interface. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* Device addresses */ +#define DEVADDR_PHY(p) (p) +#define DEVADDR_SERDES 0x0F + +/* SMI indirection registers for multichip addressing mode */ +#define SMI_CMD_REG 0x00 +#define SMI_DATA_REG 0x01 + +/* Global registers */ +#define GLOBAL1_STATUS 0x00 +#define GLOBAL1_CTRL 0x04 + +/* Global 2 registers */ +#define GLOBAL2_REG_PHY_CMD 0x18 +#define GLOBAL2_REG_PHY_DATA 0x19 +#define GLOBAL2_REG_SCRATCH 0x1A + +/* Port registers */ +#define PORT_REG_STATUS 0x00 +#define PORT_REG_PHYS_CTRL 0x01 +#define PORT_REG_SWITCH_ID 0x03 +#define PORT_REG_CTRL 0x04 + +/* Phy registers */ +#define PHY_REG_PAGE 0x16 + +/* Phy page numbers */ +#define PHY_PAGE_COPPER 0 +#define PHY_PAGE_SERDES 1 + +/* Register fields */ +#define GLOBAL1_CTRL_SWRESET BIT(15) + +#define PORT_REG_STATUS_SPEED_SHIFT 8 +#define PORT_REG_STATUS_SPEED_10 0 +#define PORT_REG_STATUS_SPEED_100 1 +#define PORT_REG_STATUS_SPEED_1000 2 + +#define PORT_REG_STATUS_CMODE_MASK 0xF +#define PORT_REG_STATUS_CMODE_SGMII 0xa +#define PORT_REG_STATUS_CMODE_1000BASE_X 0x9 +#define PORT_REG_STATUS_CMODE_100BASE_X 0x8 +#define PORT_REG_STATUS_CMODE_RGMII 0x7 +#define PORT_REG_STATUS_CMODE_RMII 0x5 +#define PORT_REG_STATUS_CMODE_RMII_PHY 0x4 +#define PORT_REG_STATUS_CMODE_GMII 0x3 +#define PORT_REG_STATUS_CMODE_MII 0x2 +#define PORT_REG_STATUS_CMODE_MIIPHY 0x1 + +#define PORT_REG_PHYS_CTRL_RGMII_DELAY_RXCLK BIT(15) +#define PORT_REG_PHYS_CTRL_RGMII_DELAY_TXCLK BIT(14) +#define PORT_REG_PHYS_CTRL_PCS_AN_EN BIT(10) +#define PORT_REG_PHYS_CTRL_PCS_AN_RST BIT(9) +#define PORT_REG_PHYS_CTRL_FC_VALUE BIT(7) +#define PORT_REG_PHYS_CTRL_FC_FORCE BIT(6) +#define PORT_REG_PHYS_CTRL_LINK_VALUE BIT(5) +#define PORT_REG_PHYS_CTRL_LINK_FORCE BIT(4) +#define PORT_REG_PHYS_CTRL_DUPLEX_VALUE BIT(3) +#define PORT_REG_PHYS_CTRL_DUPLEX_FORCE BIT(2) +#define PORT_REG_PHYS_CTRL_SPD1000 BIT(1) +#define PORT_REG_PHYS_CTRL_SPD100 BIT(0) +#define PORT_REG_PHYS_CTRL_SPD_MASK (BIT(1) | BIT(0)) + +#define PORT_REG_CTRL_PSTATE_SHIFT 0 +#define PORT_REG_CTRL_PSTATE_MASK 3 + +/* Field values */ +#define PORT_REG_CTRL_PSTATE_DISABLED 0 +#define PORT_REG_CTRL_PSTATE_FORWARD 3 + +/* + * Macros for building commands for indirect addressing modes. These are valid + * for both the indirect multichip addressing mode and the PHY indirection + * required for the writes to any PHY register. + */ +#define SMI_BUSY BIT(15) +#define SMI_CMD_CLAUSE_22 BIT(12) +#define SMI_CMD_CLAUSE_22_OP_READ (2 << 10) +#define SMI_CMD_CLAUSE_22_OP_WRITE (1 << 10) +#define SMI_CMD_ADDR_SHIFT 5 +#define SMI_CMD_ADDR_MASK 0x1f +#define SMI_CMD_REG_SHIFT 0 +#define SMI_CMD_REG_MASK 0x1f +#define SMI_CMD_READ(addr, reg) \ + (SMI_BUSY | SMI_CMD_CLAUSE_22 | SMI_CMD_CLAUSE_22_OP_READ) | \ + (((addr) & SMI_CMD_ADDR_MASK) << SMI_CMD_ADDR_SHIFT) | \ + (((reg) & SMI_CMD_REG_MASK) << SMI_CMD_REG_SHIFT) +#define SMI_CMD_WRITE(addr, reg) \ + (SMI_BUSY | SMI_CMD_CLAUSE_22 | SMI_CMD_CLAUSE_22_OP_WRITE) | \ + (((addr) & SMI_CMD_ADDR_MASK) << SMI_CMD_ADDR_SHIFT) | \ + (((reg) & SMI_CMD_REG_MASK) << SMI_CMD_REG_SHIFT) + +/* ID register values for different switch models */ +#define PORT_SWITCH_ID_6020 0x0200 +#define PORT_SWITCH_ID_6070 0x0700 +#define PORT_SWITCH_ID_6071 0x0710 +#define PORT_SWITCH_ID_6096 0x0980 +#define PORT_SWITCH_ID_6097 0x0990 +#define PORT_SWITCH_ID_6172 0x1720 +#define PORT_SWITCH_ID_6176 0x1760 +#define PORT_SWITCH_ID_6220 0x2200 +#define PORT_SWITCH_ID_6240 0x2400 +#define PORT_SWITCH_ID_6250 0x2500 +#define PORT_SWITCH_ID_6320 0x1150 +#define PORT_SWITCH_ID_6352 0x3520 + +struct mv88e6xxx_priv { + int smi_addr; + int id; + int port_count; /* Number of switch ports */ + int port_reg_base; /* Base of the switch port registers */ + u8 global1; /* Offset of Switch Global 1 registers */ + u8 global2; /* Offset of Switch Global 2 registers */ +}; + +/* Wait for the current SMI indirect command to complete */ +static int mv88e6xxx_smi_wait(struct udevice *dev, int smi_addr) +{ + int val; + u32 timeout = 100; + + do { + val = dm_mdio_read(dev->parent, smi_addr, MDIO_DEVAD_NONE, SMI_CMD_REG); + if (val >= 0 && (val & SMI_BUSY) == 0) + return 0; + + mdelay(1); + } while (--timeout); + + dev_err(dev, "SMI busy timeout\n"); + return -ETIMEDOUT; +} + +/* + * The mv88e6xxx has three types of addresses: the smi bus address, the device + * address, and the register address. The smi bus address distinguishes it on + * the smi bus from other PHYs or switches. The device address determines + * which on-chip register set you are reading/writing (the various PHYs, their + * associated ports, or global configuration registers). The register address + * is the offset of the register you are reading/writing. + * + * When the mv88e6xxx is hardware configured to have address zero, it behaves in + * single-chip addressing mode, where it responds to all SMI addresses, using + * the smi address as its device address. This obviously only works when this + * is the only chip on the SMI bus. This allows the driver to access device + * registers without using indirection. When the chip is configured to a + * non-zero address, it only responds to that SMI address and requires indirect + * writes to access the different device addresses. + */ +static int mv88e6xxx_reg_read(struct udevice *dev, int addr, int reg) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int smi_addr = priv->smi_addr; + int res; + + /* In single-chip mode, the device can be addressed directly */ + if (smi_addr == 0) + return dm_mdio_read(dev->parent, addr, MDIO_DEVAD_NONE, reg); + + /* Wait for the bus to become free */ + res = mv88e6xxx_smi_wait(dev, smi_addr); + if (res < 0) + return res; + + /* Issue the read command */ + res = dm_mdio_write(dev->parent, smi_addr, MDIO_DEVAD_NONE, SMI_CMD_REG, + SMI_CMD_READ(addr, reg)); + if (res < 0) + return res; + + /* Wait for the read command to complete */ + res = mv88e6xxx_smi_wait(dev, smi_addr); + if (res < 0) + return res; + + /* Read the data */ + res = dm_mdio_read(dev->parent, smi_addr, MDIO_DEVAD_NONE, SMI_DATA_REG); + if (res < 0) + return res; + + return res & 0xffff; +} + +/* See the comment above mv88e6xxx_reg_read */ +static int mv88e6xxx_reg_write(struct udevice *dev, int addr, int reg, u16 val) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int smi_addr = priv->smi_addr; + int res; + + /* In single-chip mode, the device can be addressed directly */ + if (smi_addr == 0) + return dm_mdio_write(dev->parent, addr, MDIO_DEVAD_NONE, reg, val); + + /* Wait for the bus to become free */ + res = mv88e6xxx_smi_wait(dev, smi_addr); + if (res < 0) + return res; + + /* Set the data to write */ + res = dm_mdio_write(dev->parent, smi_addr, MDIO_DEVAD_NONE, + SMI_DATA_REG, val); + if (res < 0) + return res; + + /* Issue the write command */ + res = dm_mdio_write(dev->parent, smi_addr, MDIO_DEVAD_NONE, SMI_CMD_REG, + SMI_CMD_WRITE(addr, reg)); + if (res < 0) + return res; + + /* Wait for the write command to complete */ + res = mv88e6xxx_smi_wait(dev, smi_addr); + if (res < 0) + return res; + + return 0; +} + +static int mv88e6xxx_phy_wait(struct udevice *dev) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int val; + u32 timeout = 100; + + do { + val = mv88e6xxx_reg_read(dev, priv->global2, GLOBAL2_REG_PHY_CMD); + if (val >= 0 && (val & SMI_BUSY) == 0) + return 0; + + mdelay(1); + } while (--timeout); + + return -ETIMEDOUT; +} + +static int mv88e6xxx_phy_read_indirect(struct udevice *dev, int phyad, int devad, int reg) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int res; + + /* Issue command to read */ + res = mv88e6xxx_reg_write(dev, priv->global2, + GLOBAL2_REG_PHY_CMD, + SMI_CMD_READ(phyad, reg)); + + /* Wait for data to be read */ + res = mv88e6xxx_phy_wait(dev); + if (res < 0) + return res; + + /* Read retrieved data */ + return mv88e6xxx_reg_read(dev, priv->global2, + GLOBAL2_REG_PHY_DATA); +} + +static int mv88e6xxx_phy_write_indirect(struct udevice *dev, int phyad, + int devad, int reg, u16 data) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int res; + + /* Set the data to write */ + res = mv88e6xxx_reg_write(dev, priv->global2, + GLOBAL2_REG_PHY_DATA, data); + if (res < 0) + return res; + /* Issue the write command */ + res = mv88e6xxx_reg_write(dev, priv->global2, + GLOBAL2_REG_PHY_CMD, + SMI_CMD_WRITE(phyad, reg)); + if (res < 0) + return res; + + /* Wait for command to complete */ + return mv88e6xxx_phy_wait(dev); +} + +/* Wrapper function to make calls to phy_read_indirect simpler */ +static int mv88e6xxx_phy_read(struct udevice *dev, int phy, int reg) +{ + return mv88e6xxx_phy_read_indirect(dev, DEVADDR_PHY(phy), + MDIO_DEVAD_NONE, reg); +} + +/* Wrapper function to make calls to phy_write_indirect simpler */ +static int mv88e6xxx_phy_write(struct udevice *dev, int phy, int reg, u16 val) +{ + return mv88e6xxx_phy_write_indirect(dev, DEVADDR_PHY(phy), + MDIO_DEVAD_NONE, reg, val); +} + +static int mv88e6xxx_port_read(struct udevice *dev, u8 port, u8 reg) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + + return mv88e6xxx_reg_read(dev, priv->port_reg_base + port, reg); +} + +static int mv88e6xxx_port_write(struct udevice *dev, u8 port, u8 reg, u16 val) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + + return mv88e6xxx_reg_write(dev, priv->port_reg_base + port, reg, val); +} + +static int mv88e6xxx_set_page(struct udevice *dev, u8 phy, u8 page) +{ + return mv88e6xxx_phy_write(dev, phy, PHY_REG_PAGE, page); +} + +static int mv88e6xxx_get_switch_id(struct udevice *dev) +{ + int res; + + res = mv88e6xxx_port_read(dev, 0, PORT_REG_SWITCH_ID); + if (res < 0) { + dev_err(dev, "Failed to read switch ID: %d\n", res); + return res; + } + return res & 0xfff0; +} + +static bool mv88e6xxx_6352_family(struct udevice *dev) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + + switch (priv->id) { + case PORT_SWITCH_ID_6172: + case PORT_SWITCH_ID_6176: + case PORT_SWITCH_ID_6240: + case PORT_SWITCH_ID_6352: + return true; + } + return false; +} + +static int mv88e6xxx_get_cmode(struct udevice *dev, u8 port) +{ + int res; + + res = mv88e6xxx_port_read(dev, port, PORT_REG_STATUS); + if (res < 0) + return res; + return res & PORT_REG_STATUS_CMODE_MASK; +} + +static int mv88e6xxx_switch_reset(struct udevice *dev) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int time_ms; + int val; + u8 port; + + /* Disable all ports */ + for (port = 0; port < priv->port_count; port++) { + val = mv88e6xxx_port_read(dev, port, PORT_REG_CTRL); + if (val < 0) + return val; + val &= ~(PORT_REG_CTRL_PSTATE_MASK << PORT_REG_CTRL_PSTATE_SHIFT); + val |= (PORT_REG_CTRL_PSTATE_DISABLED << PORT_REG_CTRL_PSTATE_SHIFT); + val = mv88e6xxx_port_write(dev, port, PORT_REG_CTRL, val); + if (val < 0) + return val; + } + + /* Wait 2 ms for queues to drain */ + udelay(2000); + + /* Reset switch */ + val = mv88e6xxx_reg_read(dev, priv->global1, GLOBAL1_CTRL); + if (val < 0) + return val; + val |= GLOBAL1_CTRL_SWRESET; + val = mv88e6xxx_reg_write(dev, priv->global1, GLOBAL1_CTRL, val); + if (val < 0) + return val; + + /* Wait up to 1 second for switch to reset complete */ + for (time_ms = 1000; time_ms; time_ms--) { + val = mv88e6xxx_reg_read(dev, priv->global1, GLOBAL1_CTRL); + if (val >= 0 && ((val & GLOBAL1_CTRL_SWRESET) == 0)) + break; + udelay(1000); + } + if (!time_ms) + return -ETIMEDOUT; + + return 0; +} + +static int mv88e6xxx_serdes_init(struct udevice *dev) +{ + int val; + + val = mv88e6xxx_set_page(dev, DEVADDR_SERDES, PHY_PAGE_SERDES); + if (val < 0) + return val; + + /* Power up serdes module */ + val = mv88e6xxx_phy_read(dev, DEVADDR_SERDES, MII_BMCR); + if (val < 0) + return val; + val &= ~(BMCR_PDOWN); + val = mv88e6xxx_phy_write(dev, DEVADDR_SERDES, MII_BMCR, val); + if (val < 0) + return val; + + return 0; +} + +/* + * This function is used to pre-configure the required register + * offsets, so that the indirect register access to the PHY registers + * is possible. This is necessary to be able to read the PHY ID + * while driver probing or in get_phy_id(). The globalN register + * offsets must be initialized correctly for a detected switch, + * otherwise detection of the PHY ID won't work! + */ +static int mv88e6xxx_priv_reg_offs_pre_init(struct udevice *dev) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + + /* + * Initial 'port_reg_base' value must be an offset of existing + * port register, then reading the ID should succeed. First, try + * to read via port registers with device address 0x10 (88E6096 + * and compatible switches). + */ + priv->port_reg_base = 0x10; + priv->id = mv88e6xxx_get_switch_id(dev); + if (priv->id != 0xfff0) { + priv->global1 = 0x1B; + priv->global2 = 0x1C; + return 0; + } + + /* + * Now try via port registers with device address 0x08 + * (88E6020 and compatible switches). + */ + priv->port_reg_base = 0x08; + priv->id = mv88e6xxx_get_switch_id(dev); + if (priv->id != 0xfff0) { + priv->global1 = 0x0F; + priv->global2 = 0x07; + return 0; + } + + dev_warn(dev, "%s Unknown ID 0x%x\n", __func__, priv->id); + + return -ENODEV; +} + +static int mv88e6xxx_mdio_read(struct udevice *dev, int addr, int devad, int reg) +{ + return mv88e6xxx_phy_read_indirect(dev->parent, DEVADDR_PHY(addr), + MDIO_DEVAD_NONE, reg); +} + +static int mv88e6xxx_mdio_write(struct udevice *dev, int addr, int devad, + int reg, u16 val) +{ + return mv88e6xxx_phy_write_indirect(dev->parent, DEVADDR_PHY(addr), + MDIO_DEVAD_NONE, reg, val); +} + +static const struct mdio_ops mv88e6xxx_mdio_ops = { + .read = mv88e6xxx_mdio_read, + .write = mv88e6xxx_mdio_write, +}; + +static int mv88e6xxx_mdio_bind(struct udevice *dev) +{ + char name[32]; + static int num_devices; + + sprintf(name, "mv88e6xxx-mdio-%d", num_devices++); + device_set_name(dev, name); + + return 0; +} + +U_BOOT_DRIVER(mv88e6xxx_mdio) = { + .name = "mv88e6xxx_mdio", + .id = UCLASS_MDIO, + .ops = &mv88e6xxx_mdio_ops, + .bind = mv88e6xxx_mdio_bind, + .plat_auto = sizeof(struct mdio_perdev_priv), +}; + +static int mv88e6xxx_port_probe(struct udevice *dev, int port, struct phy_device *phy) +{ + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int supported; + + switch (priv->id) { + case PORT_SWITCH_ID_6020: + case PORT_SWITCH_ID_6070: + case PORT_SWITCH_ID_6071: + supported = PHY_BASIC_FEATURES | SUPPORTED_MII; + break; + default: + supported = PHY_GBIT_FEATURES; + break; + } + + phy->supported &= supported; + phy->advertising &= supported; + + return phy_config(phy); +} + +static int mv88e6xxx_port_enable(struct udevice *dev, int port, struct phy_device *phy) +{ + int val, ret; + + dev_dbg(dev, "%s P%d phy:0x%08x %s\n", __func__, port, + phy->phy_id, phy_string_for_interface(phy->interface)); + + if (phy->phy_id == PHY_FIXED_ID) { + /* Physical Control register: Table 62 */ + val = mv88e6xxx_port_read(dev, port, PORT_REG_PHYS_CTRL); + + /* configure RGMII delays for fixed link */ + switch (phy->interface) { + case PHY_INTERFACE_MODE_RGMII: + case PHY_INTERFACE_MODE_RGMII_ID: + case PHY_INTERFACE_MODE_RGMII_RXID: + case PHY_INTERFACE_MODE_RGMII_TXID: + dev_dbg(dev, "configure internal RGMII delays\n"); + + /* RGMII delays */ + val &= ~(PORT_REG_PHYS_CTRL_RGMII_DELAY_RXCLK || + PORT_REG_PHYS_CTRL_RGMII_DELAY_TXCLK); + if (phy->interface == PHY_INTERFACE_MODE_RGMII_ID || + phy->interface == PHY_INTERFACE_MODE_RGMII_RXID) + val |= PORT_REG_PHYS_CTRL_RGMII_DELAY_RXCLK; + if (phy->interface == PHY_INTERFACE_MODE_RGMII_ID || + phy->interface == PHY_INTERFACE_MODE_RGMII_TXID) + val |= PORT_REG_PHYS_CTRL_RGMII_DELAY_TXCLK; + break; + default: + break; + } + + /* Force Link */ + val |= PORT_REG_PHYS_CTRL_LINK_VALUE | + PORT_REG_PHYS_CTRL_LINK_FORCE; + + ret = mv88e6xxx_port_write(dev, port, PORT_REG_PHYS_CTRL, val); + if (ret < 0) + return ret; + + if (mv88e6xxx_6352_family(dev)) { + /* validate interface type */ + dev_dbg(dev, "validate interface type\n"); + val = mv88e6xxx_get_cmode(dev, port); + if (val < 0) + return val; + switch (phy->interface) { + case PHY_INTERFACE_MODE_RGMII: + case PHY_INTERFACE_MODE_RGMII_RXID: + case PHY_INTERFACE_MODE_RGMII_TXID: + case PHY_INTERFACE_MODE_RGMII_ID: + if (val != PORT_REG_STATUS_CMODE_RGMII) + goto mismatch; + break; + case PHY_INTERFACE_MODE_1000BASEX: + if (val != PORT_REG_STATUS_CMODE_1000BASE_X) + goto mismatch; + break; +mismatch: + default: + dev_err(dev, "Mismatched PHY mode %s on port %d!\n", + phy_string_for_interface(phy->interface), port); + break; + } + } + } + + /* enable port */ + val = mv88e6xxx_port_read(dev, port, PORT_REG_CTRL); + if (val < 0) + return val; + val &= ~(PORT_REG_CTRL_PSTATE_MASK << PORT_REG_CTRL_PSTATE_SHIFT); + val |= (PORT_REG_CTRL_PSTATE_FORWARD << PORT_REG_CTRL_PSTATE_SHIFT); + val = mv88e6xxx_port_write(dev, port, PORT_REG_CTRL, val); + if (val < 0) + return val; + + return phy_startup(phy); +} + +static void mv88e6xxx_port_disable(struct udevice *dev, int port, struct phy_device *phy) +{ + int val; + + dev_dbg(dev, "%s P%d phy:0x%08x %s\n", __func__, port, + phy->phy_id, phy_string_for_interface(phy->interface)); + + val = mv88e6xxx_port_read(dev, port, PORT_REG_CTRL); + val &= ~(PORT_REG_CTRL_PSTATE_MASK << PORT_REG_CTRL_PSTATE_SHIFT); + val |= (PORT_REG_CTRL_PSTATE_DISABLED << PORT_REG_CTRL_PSTATE_SHIFT); + mv88e6xxx_port_write(dev, port, PORT_REG_CTRL, val); +} + +static const struct dsa_ops mv88e6xxx_dsa_ops = { + .port_probe = mv88e6xxx_port_probe, + .port_enable = mv88e6xxx_port_enable, + .port_disable = mv88e6xxx_port_disable, +}; + +/* bind and probe the switch mdios */ +static int mv88e6xxx_probe_mdio(struct udevice *dev) +{ + struct udevice *mdev; + const char *name; + ofnode node; + int ret; + + /* bind phy ports of mdio child node to mv88e6xxx_mdio device */ + node = dev_read_subnode(dev, "mdio"); + if (!ofnode_valid(node)) + return 0; + + name = ofnode_get_name(node); + ret = device_bind_driver_to_node(dev, + "mv88e6xxx_mdio", + name, node, NULL); + if (ret) { + dev_err(dev, "failed to bind %s: %d\n", name, ret); + } else { + /* need to probe it as there is no compatible to do so */ + ret = uclass_get_device_by_ofnode(UCLASS_MDIO, node, &mdev); + if (ret) + dev_err(dev, "failed to probe %s: %d\n", name, ret); + } + + return ret; +} + +static int mv88e6xxx_probe(struct udevice *dev) +{ + struct dsa_pdata *dsa_pdata = dev_get_uclass_plat(dev); + struct mv88e6xxx_priv *priv = dev_get_priv(dev); + int val, ret; + + if (ofnode_valid(dev_ofnode(dev)) && + !ofnode_is_enabled(dev_ofnode(dev))) { + dev_dbg(dev, "switch disabled\n"); + return -ENODEV; + } + + /* probe internal mdio bus */ + ret = mv88e6xxx_probe_mdio(dev); + if (ret) + return ret; + + ret = mv88e6xxx_priv_reg_offs_pre_init(dev); + if (ret) + return ret; + + dev_dbg(dev, "ID=0x%x PORT_BASE=0x%02x GLOBAL1=0x%02x GLOBAL2=0x%02x\n", + priv->id, priv->port_reg_base, priv->global1, priv->global2); + switch (priv->id) { + case PORT_SWITCH_ID_6096: + case PORT_SWITCH_ID_6097: + case PORT_SWITCH_ID_6172: + case PORT_SWITCH_ID_6176: + case PORT_SWITCH_ID_6240: + case PORT_SWITCH_ID_6352: + priv->port_count = 11; + break; + case PORT_SWITCH_ID_6020: + case PORT_SWITCH_ID_6070: + case PORT_SWITCH_ID_6071: + case PORT_SWITCH_ID_6220: + case PORT_SWITCH_ID_6250: + case PORT_SWITCH_ID_6320: + priv->port_count = 7; + break; + default: + return -ENODEV; + } + + ret = mv88e6xxx_switch_reset(dev); + if (ret < 0) + return ret; + + if (mv88e6xxx_6352_family(dev)) { + val = mv88e6xxx_get_cmode(dev, dsa_pdata->cpu_port); + if (val < 0) + return val; + /* initialize serdes */ + if (val == PORT_REG_STATUS_CMODE_100BASE_X || + val == PORT_REG_STATUS_CMODE_1000BASE_X || + val == PORT_REG_STATUS_CMODE_SGMII) { + ret = mv88e6xxx_serdes_init(dev); + if (ret < 0) + return ret; + } + } + + return 0; +} + +static const struct udevice_id mv88e6xxx_ids[] = { + { .compatible = "marvell,mv88e6085" }, + { } +}; + +U_BOOT_DRIVER(mv88e6xxx) = { + .name = "mv88e6xxx", + .id = UCLASS_DSA, + .of_match = mv88e6xxx_ids, + .probe = mv88e6xxx_probe, + .ops = &mv88e6xxx_dsa_ops, + .priv_auto = sizeof(struct mv88e6xxx_priv), +}; From patchwork Wed Nov 30 17:42:51 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Tim Harvey X-Patchwork-Id: 1710629 X-Patchwork-Delegate: trini@ti.com Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=lists.denx.de (client-ip=85.214.62.61; helo=phobos.denx.de; envelope-from=u-boot-bounces@lists.denx.de; receiver=) Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-384)) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4NMmmJ5hygz23nT for ; Thu, 1 Dec 2022 04:44:16 +1100 (AEDT) Received: from h2850616.stratoserver.net (localhost [IPv6:::1]) by phobos.denx.de (Postfix) with ESMTP id 06747853D5; Wed, 30 Nov 2022 18:43:22 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=u-boot-bounces@lists.denx.de Received: by phobos.denx.de (Postfix, from userid 109) id 0FF73853D5; Wed, 30 Nov 2022 18:43:08 +0100 (CET) X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on phobos.denx.de X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00,SPF_HELO_NONE, SPF_PASS autolearn=ham autolearn_force=no version=3.4.2 Received: from finn.localdomain (finn.gateworks.com [108.161.129.64]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) by phobos.denx.de (Postfix) with ESMTPS id 0007B83A30 for ; Wed, 30 Nov 2022 18:43:02 +0100 (CET) Authentication-Results: phobos.denx.de; dmarc=none (p=none dis=none) header.from=gateworks.com Authentication-Results: phobos.denx.de; spf=pass smtp.mailfrom=tharvey@gateworks.com Received: from 068-189-091-139.biz.spectrum.com ([68.189.91.139] helo=tharvey.pdc.gateworks.com) by finn.localdomain with esmtp (Exim 4.93) (envelope-from ) id 1p0R6q-0016xU-Gb; Wed, 30 Nov 2022 17:43:00 +0000 From: Tim Harvey To: u-boot@lists.denx.de, Joe Hershberger , Ramon Fried , Vladimir Oltean , Stefano Babic , Fabio Estevam , "NXP i . MX U-Boot Team" , =?utf-8?q?Marek_Beh=C3=BAn?= Cc: Tim Harvey , Fabio Estevam Subject: [PATCH v9 8/8] board: gw_ventana: enable MV88E61XX DSA support Date: Wed, 30 Nov 2022 09:42:51 -0800 Message-Id: <20221130174251.82087-9-tharvey@gateworks.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20221130174251.82087-1-tharvey@gateworks.com> References: <20221130174251.82087-1-tharvey@gateworks.com> MIME-Version: 1.0 X-BeenThere: u-boot@lists.denx.de X-Mailman-Version: 2.1.39 Precedence: list List-Id: U-Boot discussion List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: u-boot-bounces@lists.denx.de Sender: "U-Boot" X-Virus-Scanned: clamav-milter 0.103.6 at phobos.denx.de X-Virus-Status: Clean Add MV88E61XX DSA support: - update dt to provide internal MDIO bus and port handles. U-Boot requires a more restrictive subset of the dt bindings required by Linux for the sake of simplifying code - update defconfig to remove old driver and enable new one - replace mv88e61xx_hw_reset weak override with board_phy_config support for register configuration that is outside the scope of the DSA driver Signed-off-by: Tim Harvey Reviewed-by: Fabio Estevam Reviewed-by: Vladimir Oltean --- v9: - no changes v8: - added phy-mode = "internal" to phy ports v7: - added Vladimir's rb tag v6: - update commit message - squash accidently change to mv88e6xxx driver into previous patch - remove unused label for cpu port v5: - fix typo in defconfig s/MV88E61XX/MV88E6XXX - added Fabio's rb tag v4: - use standard Linux internal MDIO dt structure - use PHY_FIXED_ID define v3: - move mdio's mdio@0 subnode v2: no changes --- arch/arm/dts/imx6qdl-gw5904.dtsi | 36 +++++++++++++++++- board/gateworks/gw_ventana/gw_ventana.c | 50 +++++++++---------------- configs/gwventana_gw5904_defconfig | 7 ++-- 3 files changed, 56 insertions(+), 37 deletions(-) diff --git a/arch/arm/dts/imx6qdl-gw5904.dtsi b/arch/arm/dts/imx6qdl-gw5904.dtsi index 612b6e068e28..ea54922f15f8 100644 --- a/arch/arm/dts/imx6qdl-gw5904.dtsi +++ b/arch/arm/dts/imx6qdl-gw5904.dtsi @@ -212,6 +212,27 @@ compatible = "marvell,mv88e6085"; reg = <0>; + mdio { + #address-cells = <1>; + #size-cells = <0>; + + sw_phy0: ethernet-phy@0 { + reg = <0x0>; + }; + + sw_phy1: ethernet-phy@1 { + reg = <0x1>; + }; + + sw_phy2: ethernet-phy@2 { + reg = <0x2>; + }; + + sw_phy3: ethernet-phy@3 { + reg = <0x3>; + }; + }; + ports { #address-cells = <1>; #size-cells = <0>; @@ -219,27 +240,40 @@ port@0 { reg = <0>; label = "lan4"; + phy-handle = <&sw_phy0>; + phy-mode = "internal"; }; port@1 { reg = <1>; label = "lan3"; + phy-handle = <&sw_phy1>; + phy-mode = "internal"; }; port@2 { reg = <2>; label = "lan2"; + phy-handle = <&sw_phy2>; + phy-mode = "internal"; }; port@3 { reg = <3>; label = "lan1"; + phy-handle = <&sw_phy3>; + phy-mode = "internal"; }; port@5 { reg = <5>; - label = "cpu"; ethernet = <&fec>; + phy-mode = "rgmii-id"; + + fixed-link { + speed = <1000>; + full-duplex; + }; }; }; }; diff --git a/board/gateworks/gw_ventana/gw_ventana.c b/board/gateworks/gw_ventana/gw_ventana.c index 0ecfd98c2261..683def7e9f71 100644 --- a/board/gateworks/gw_ventana/gw_ventana.c +++ b/board/gateworks/gw_ventana/gw_ventana.c @@ -83,44 +83,30 @@ int board_phy_config(struct phy_device *phydev) break; } + /* Fixed PHY: for GW5904/GW5909 this is Marvell 88E6176 GbE Switch */ + if (phydev->phy_id == PHY_FIXED_ID && + (board_type == GW5904 || board_type == GW5909)) { + struct mii_dev *bus = miiphy_get_dev_by_name("mdio"); + + puts("MV88E61XX "); + /* GPIO[0] output CLK125 for RGMII_REFCLK */ + bus->write(bus, 0x1c, 0, 0x1a, (1 << 15) | (0x62 << 8) | 0xfe); + bus->write(bus, 0x1c, 0, 0x1a, (1 << 15) | (0x68 << 8) | 7); + + /* Port 0-3 LED configuration: Table 80/82 */ + /* LED configuration: 7:4-green (8=Activity) 3:0 amber (8=Link) */ + bus->write(bus, 0x10, 0, 0x16, 0x8088); + bus->write(bus, 0x11, 0, 0x16, 0x8088); + bus->write(bus, 0x12, 0, 0x16, 0x8088); + bus->write(bus, 0x13, 0, 0x16, 0x8088); + } + if (phydev->drv->config) phydev->drv->config(phydev); return 0; } -#ifdef CONFIG_MV88E61XX_SWITCH -int mv88e61xx_hw_reset(struct phy_device *phydev) -{ - struct mii_dev *bus = phydev->bus; - - /* GPIO[0] output, CLK125 */ - debug("enabling RGMII_REFCLK\n"); - bus->write(bus, 0x1c /*MV_GLOBAL2*/, 0, - 0x1a /*MV_SCRATCH_MISC*/, - (1 << 15) | (0x62 /*MV_GPIO_DIR*/ << 8) | 0xfe); - bus->write(bus, 0x1c /*MV_GLOBAL2*/, 0, - 0x1a /*MV_SCRATCH_MISC*/, - (1 << 15) | (0x68 /*MV_GPIO01_CNTL*/ << 8) | 7); - - /* RGMII delay - Physical Control register bit[15:14] */ - debug("setting port%d RGMII rx/tx delay\n", CONFIG_MV88E61XX_CPU_PORT); - /* forced 1000mbps full-duplex link */ - bus->write(bus, 0x10 + CONFIG_MV88E61XX_CPU_PORT, 0, 1, 0xc0fe); - phydev->autoneg = AUTONEG_DISABLE; - phydev->speed = SPEED_1000; - phydev->duplex = DUPLEX_FULL; - - /* LED configuration: 7:4-green (8=Activity) 3:0 amber (8=Link) */ - bus->write(bus, 0x10, 0, 0x16, 0x8088); - bus->write(bus, 0x11, 0, 0x16, 0x8088); - bus->write(bus, 0x12, 0, 0x16, 0x8088); - bus->write(bus, 0x13, 0, 0x16, 0x8088); - - return 0; -} -#endif // CONFIG_MV88E61XX_SWITCH - #if defined(CONFIG_VIDEO_IPUV3) static void enable_hdmi(struct display_info_t const *dev) { diff --git a/configs/gwventana_gw5904_defconfig b/configs/gwventana_gw5904_defconfig index f58abd9c5e57..d2c48656de91 100644 --- a/configs/gwventana_gw5904_defconfig +++ b/configs/gwventana_gw5904_defconfig @@ -110,13 +110,12 @@ CONFIG_SUPPORT_EMMC_BOOT=y CONFIG_FSL_USDHC=y CONFIG_MTD=y CONFIG_PHYLIB=y -CONFIG_MV88E61XX_SWITCH=y -CONFIG_MV88E61XX_CPU_PORT=5 -CONFIG_MV88E61XX_PHY_PORTS=0xf -CONFIG_MV88E61XX_FIXED_PORTS=0x0 +CONFIG_PHY_FIXED=y CONFIG_DM_MDIO=y +CONFIG_DM_DSA=y CONFIG_E1000=y CONFIG_FEC_MXC=y +CONFIG_MV88E6XXX=y CONFIG_MII=y CONFIG_PCI=y CONFIG_PCIE_IMX=y