From: Oleksij Rempel <o.rempel@pengutronix.de>
To: barebox@lists.infradead.org
Cc: Oleksij Rempel <o.rempel@pengutronix.de>
Subject: [PATCH v3 3/7] ARM: boards: skov-imx6: add switch detection
Date: Mon, 20 Sep 2021 13:15:24 +0200 [thread overview]
Message-ID: <20210920111528.14575-4-o.rempel@pengutronix.de> (raw)
In-Reply-To: <20210920111528.14575-1-o.rempel@pengutronix.de>
There are board variants with same board ID but not switch. Detect this
variants.
Signed-off-by: Oleksij Rempel <o.rempel@pengutronix.de>
---
arch/arm/boards/skov-imx6/board.c | 158 +++++++++++++++++++++++++-----
1 file changed, 134 insertions(+), 24 deletions(-)
diff --git a/arch/arm/boards/skov-imx6/board.c b/arch/arm/boards/skov-imx6/board.c
index 030ac62c52..a94c2cd25c 100644
--- a/arch/arm/boards/skov-imx6/board.c
+++ b/arch/arm/boards/skov-imx6/board.c
@@ -11,6 +11,7 @@
#include <net.h>
#include <of_gpio.h>
#include <gpio.h>
+#include <linux/micrel_phy.h>
#include "version.h"
@@ -130,6 +131,9 @@ copy_mac_from_eth0:
return eth_of_fixup_node_from_eth_device(root, node_path, ethname);
}
+#define SKOV_GPIO_MDIO_BUS 0
+#define SKOV_LAN1_PHY_ADDR 1
+
#define MAX_V_GPIO 8
struct board_description {
@@ -303,20 +307,121 @@ static const struct board_description imx6_variants[] = {
};
static int skov_board_no = -1;
+static bool skov_no_switch = false;
+static const char *no_switch_suffix = "-noswitch";
-static int skov_imx6_fixup(struct device_node *root, void *unused)
+static void fixup_machine_compatible(const char *compat,
+ struct device_node *root)
{
+ int cclen = 0, clen = strlen(compat) + 1;
+ const char *curcompat;
+ void *buf;
+
+ if (!root) {
+ root = of_get_root_node();
+ if (!root)
+ return;
+ }
+
+ curcompat = of_get_property(root, "compatible", &cclen);
+
+ buf = xzalloc(cclen + clen);
+
+ memcpy(buf, compat, clen);
+ memcpy(buf + clen, curcompat, cclen);
+
+ /*
+ * Prepend the compatible from board entry to the machine compatible.
+ * Used to match bootspec entries against it.
+ */
+ of_set_property(root, "compatible", buf, cclen + clen, true);
+
+ free(buf);
+}
+
+static void fixup_noswitch_machine_compatible(struct device_node *root)
+{
+ const char *compat = imx6_variants[skov_board_no].dts_compatible;
+ const char *generic = "skov,imx6";
+ size_t size, size_generic;
+ char *buf;
int ret;
- const char *val;
- uint32_t brightness;
+
+ size = strlen(compat) + strlen(no_switch_suffix) + 1;
+ size_generic = strlen(generic) + strlen(no_switch_suffix) + 1;
+ size = max(size, size_generic);
+ buf = xzalloc(size);
+ if (!buf) {
+ pr_warn("Can't allocate buffer\n");
+ return;
+ }
+
+ /* add generic compatible, so systemd&co can make right decisions */
+ ret = snprintf(buf, size, "%s%s", generic, no_switch_suffix);
+ if (ret >= 0)
+ fixup_machine_compatible(buf, root);
+ else
+ pr_warn("Can't prepare generic compatible string\n");
+
+ /* add specific compatible as fallback, in case this board has new
+ * challenges.
+ */
+ ret = snprintf(buf, size, "%s%s", compat, no_switch_suffix);
+ if (ret >= 0)
+ fixup_machine_compatible(buf, root);
+ else
+ pr_warn("Can't prepare specific compatible string\n");
+
+ free(buf);
+}
+
+static void skov_imx6_no_switch(struct device_node *root)
+{
struct device_node *node;
- struct device_node *chosen = of_create_node(root, "/chosen");
+ int ret;
+
+ fixup_noswitch_machine_compatible(root);
+ node = of_find_node_by_path_from(root, "/soc/bus@2100000/ethernet@2188000");
+ if (!node) {
+ pr_warn("Did not find node to disable it\n");
+ } else {
+ ret = of_device_disable(node);
+ if (ret)
+ pr_warn("Can't disable ethernet node\n");
+ }
+
+ node = of_find_node_by_alias(root, "mdio-gpio0");
+ if (node) {
+ ret = of_device_disable(node);
+ if (ret)
+ pr_warn("Can't disable mdio-gpio0 node\n");
+ } else {
+ pr_warn("Can't find mdio-gpio0 node\n");
+ }
+}
+
+static void skov_imx6_switch(struct device_node *root)
+{
eth_of_fixup_node_from_eth_device(root,
"/mdio-gpio/ksz8873@3/ports/ports@0", "eth0");
eth2_of_fixup_node_individually(root,
"/mdio-gpio/ksz8873@3/ports/ports@1", "eth0",
"state.ethaddr.eth2", "/state/ethaddr/eth2");
+}
+
+static int skov_imx6_fixup(struct device_node *root, void *unused)
+{
+ struct device_node *chosen = of_create_node(root, "/chosen");
+ struct device_node *node;
+ uint32_t brightness;
+ const char *val;
+ int ret;
+
+ if (skov_no_switch)
+ skov_imx6_no_switch(root);
+ else
+ skov_imx6_switch(root);
switch (bootsource_get()) {
case BOOTSOURCE_MMC:
@@ -432,34 +537,39 @@ static void skov_init_board(const struct board_description *variant)
}
}
-static void fixup_machine_compatible(const char *compat,
- struct device_node *root)
+static int skov_switch_test(void)
{
- const char *curcompat;
- int cclen = 0, clen = strlen(compat) + 1;
- void *buf;
+ struct phy_device *phydev;
+ struct mii_bus *mii;
+ int ret;
- if (!root) {
- root = of_get_root_node();
- if (!root)
- return;
- }
+ if (skov_board_no < 0)
+ return 0;
- curcompat = of_get_property(root, "compatible", &cclen);
+ /* On this boards, we have only one MDIO bus. So, it is enough to take
+ * the first one.
+ */
+ mii = mdiobus_get_bus(SKOV_GPIO_MDIO_BUS);
+ /* We can't read the switch ID, but we get get ID of the first PHY,
+ * which is enough to test if the switch is attached.
+ */
+ phydev = get_phy_device(mii, SKOV_LAN1_PHY_ADDR);
+ if (IS_ERR(phydev))
+ goto no_switch;
- buf = xzalloc(cclen + clen);
+ if (phydev->phy_id != PHY_ID_KSZ886X)
+ goto no_switch;
- memcpy(buf, compat, clen);
- memcpy(buf + clen, curcompat, cclen);
+ return 0;
- /*
- * Prepend the compatible from board entry to the machine compatible.
- * Used to match bootspec entries against it.
- */
- of_set_property(root, "compatible", buf, cclen + clen, true);
+no_switch:
+ skov_no_switch = true;
- free(buf);
+ pr_notice("No-switch variant is detected\n");
+
+ return 0;
}
+late_initcall(skov_switch_test);
static int skov_imx6_probe(struct device_d *dev)
{
--
2.30.2
_______________________________________________
barebox mailing list
barebox@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/barebox
next prev parent reply other threads:[~2021-09-20 11:17 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-09-20 11:15 [PATCH v3 0/7] add noswitch support for skov boards Oleksij Rempel
2021-09-20 11:15 ` [PATCH v3 1/7] ARM: dts: skov-imx6: add USB nodes Oleksij Rempel
2021-09-20 11:15 ` [PATCH v3 2/7] ARM: boards: skov-imx6: fixup_machine_compatible() add optional root node Oleksij Rempel
2021-09-20 11:15 ` Oleksij Rempel [this message]
2021-10-01 14:29 ` [PATCH v3 3/7] ARM: boards: skov-imx6: add switch detection Sascha Hauer
2021-09-20 11:15 ` [PATCH v3 4/7] ARM: boards: skov-imx6: disable eth0 for barebox if no switch is detected Oleksij Rempel
2021-09-20 11:15 ` [PATCH v3 5/7] ARM: boards: skov-imx6: fixup different DTS variants Oleksij Rempel
2021-09-20 11:15 ` [PATCH v3 6/7] ARM: boards: skov-imx6: start using deep-probe Oleksij Rempel
2021-09-20 11:15 ` [PATCH v3 7/7] ARM: boards: skov-imx6: add defaultenv with eth1-discover script Oleksij Rempel
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=20210920111528.14575-4-o.rempel@pengutronix.de \
--to=o.rempel@pengutronix.de \
--cc=barebox@lists.infradead.org \
/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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox