Merge tag 'u-boot-imx-20220616' of https://gitlab.denx.de/u-boot/custodians/u-boot-imx

u-boot-imx-20220616
-------------------

Fixes for 2022.07 + Toradex apalis-imx8 (missed in last PR)

CI: https://source.denx.de/u-boot/custodians/u-boot-imx/-/pipelines/12322
diff --git a/arch/arm/dts/imx6qdl-sr-som.dtsi b/arch/arm/dts/imx6qdl-sr-som.dtsi
index b065778..c20bed2 100644
--- a/arch/arm/dts/imx6qdl-sr-som.dtsi
+++ b/arch/arm/dts/imx6qdl-sr-som.dtsi
@@ -55,7 +55,13 @@
 	pinctrl-0 = <&pinctrl_microsom_enet_ar8035>;
 	phy-handle = <&phy>;
 	phy-mode = "rgmii-id";
-	phy-reset-duration = <2>;
+
+	/*
+	 * The PHY seems to require a long-enough reset duration to avoid
+	 * some rare issues where the PHY gets stuck in an inconsistent and
+	 * non-functional state at boot-up. 10ms proved to be fine .
+	 */
+	phy-reset-duration = <10>;
 	phy-reset-gpios = <&gpio4 15 GPIO_ACTIVE_LOW>;
 	status = "okay";
 
@@ -64,8 +70,15 @@
 		#size-cells = <0>;
 
 		phy: ethernet-phy@0 {
-			reg = <0>;
+			/*
+			 * The PHY can appear either:
+			 * - AR8035: at address 0 or 4
+			 * - ADIN1300: at address 1
+			 * Actual address being detected at runtime.
+			 */
+			reg = <0xffffffff>;
 			qca,clk-out-frequency = <125000000>;
+			adi,phy-output-clock = "125mhz-free-running";
 		};
 	};
 };
diff --git a/arch/arm/dts/imx8mn-evk-u-boot.dtsi b/arch/arm/dts/imx8mn-evk-u-boot.dtsi
index 3db46d4..593cf06 100644
--- a/arch/arm/dts/imx8mn-evk-u-boot.dtsi
+++ b/arch/arm/dts/imx8mn-evk-u-boot.dtsi
@@ -58,7 +58,9 @@
 	};
 
 
-	flash {
+	spl {
+		filename = "spl.bin";
+
 		mkimage {
 			args = "-n spl/u-boot-spl.cfgout -T imx8mimage -e 0x912000";
 
diff --git a/board/freescale/common/Kconfig b/board/freescale/common/Kconfig
index 6553bf6..b0e6e43 100644
--- a/board/freescale/common/Kconfig
+++ b/board/freescale/common/Kconfig
@@ -3,6 +3,7 @@
 	imply CMD_BLOB
 	imply CMD_HASH if ARM
 	select FSL_CAAM
+	select ARCH_MISC_INIT
 	select SPL_BOARD_INIT if (ARM && SPL)
 	select SPL_HASH if (ARM && SPL)
 	select SHA_HW_ACCEL
diff --git a/board/solidrun/mx6cuboxi/mx6cuboxi.c b/board/solidrun/mx6cuboxi/mx6cuboxi.c
index 6207bf8..42aa5cb 100644
--- a/board/solidrun/mx6cuboxi/mx6cuboxi.c
+++ b/board/solidrun/mx6cuboxi/mx6cuboxi.c
@@ -1,5 +1,7 @@
 // SPDX-License-Identifier: GPL-2.0+
 /*
+ * Copyright (C) 2022 Josua Mayer <josua@solid-run.com>
+ *
  * Copyright (C) 2015 Freescale Semiconductor, Inc.
  *
  * Author: Fabio Estevam <fabio.estevam@freescale.com>
@@ -39,6 +41,8 @@
 #include <spl.h>
 #include <usb.h>
 #include <usb/ehci-ci.h>
+#include <netdev.h>
+#include <phy.h>
 
 DECLARE_GLOBAL_DATA_PTR;
 
@@ -407,6 +411,80 @@
 	return 0;
 }
 
+static int find_ethernet_phy(void)
+{
+	struct mii_dev *bus = NULL;
+	struct phy_device *phydev = NULL;
+	int phy_addr = -ENOENT;
+
+#ifdef CONFIG_FEC_MXC
+	bus = fec_get_miibus(ENET_BASE_ADDR, -1);
+	if (!bus)
+		return -ENOENT;
+
+	// scan address 0, 1, 4
+	phydev = phy_find_by_mask(bus, 0b00010011);
+	if (!phydev) {
+		free(bus);
+		return -ENOENT;
+	}
+	pr_debug("%s: detected ethernet phy at address %d\n", __func__, phydev->addr);
+	phy_addr = phydev->addr;
+
+	free(phydev);
+#endif
+
+	return phy_addr;
+}
+
+#if defined(CONFIG_OF_LIBFDT) && defined(CONFIG_OF_BOARD_SETUP)
+/*
+ * Configure the correct ethernet PHYs nodes in device-tree:
+ * - AR8035 at addresses 0 or 4: Cubox
+ * - AR8035 at address 0: HummingBoard, HummingBoard 2
+ * - ADIN1300 at address 1: since SoM rev 1.9
+ */
+int ft_board_setup(void *fdt, struct bd_info *bd)
+{
+	int node_phy0, node_phy1, node_phy4;
+	int ret, phy;
+	bool enable_phy0 = false, enable_phy1 = false, enable_phy4 = false;
+
+	// detect phy
+	phy = find_ethernet_phy();
+	if (phy == 0 || phy == 4) {
+		enable_phy0 = true;
+		switch (board_type()) {
+		case CUBOXI:
+		case UNKNOWN:
+		default:
+			enable_phy4 = true;
+		}
+	} else if (phy == 1) {
+		enable_phy1 = true;
+	} else {
+		pr_err("%s: couldn't detect ethernet phy, not patching dtb!\n", __func__);
+		return 0;
+	}
+
+	// update all phy nodes status
+	node_phy0 = fdt_path_offset(fdt, "/soc/bus@2100000/ethernet@2188000/mdio/ethernet-phy@0");
+	ret = fdt_setprop_string(fdt, node_phy0, "status", enable_phy0 ? "okay" : "disabled");
+	if (ret < 0 && enable_phy0)
+		pr_err("%s: failed to enable ethernet phy at address 0 in dtb!\n", __func__);
+	node_phy1 = fdt_path_offset(fdt, "/soc/bus@2100000/ethernet@2188000/mdio/ethernet-phy@1");
+	ret = fdt_setprop_string(fdt, node_phy1, "status", enable_phy1 ? "okay" : "disabled");
+	if (ret < 0 && enable_phy1)
+		pr_err("%s: failed to enable ethernet phy at address 1 in dtb!\n", __func__);
+	node_phy4 = fdt_path_offset(fdt, "/soc/bus@2100000/ethernet@2188000/mdio/ethernet-phy@4");
+	ret = fdt_setprop_string(fdt, node_phy4, "status", enable_phy4 ? "okay" : "disabled");
+	if (ret < 0 && enable_phy4)
+		pr_err("%s: failed to enable ethernet phy at address 4 in dtb!\n", __func__);
+
+	return 0;
+}
+#endif
+
 /* Override the default implementation, DT model is not accurate */
 int show_board_info(void)
 {
diff --git a/board/toradex/apalis-imx8/apalis-imx8.c b/board/toradex/apalis-imx8/apalis-imx8.c
index 04877fc..4081988 100644
--- a/board/toradex/apalis-imx8/apalis-imx8.c
+++ b/board/toradex/apalis-imx8/apalis-imx8.c
@@ -18,6 +18,7 @@
 #include <env.h>
 #include <errno.h>
 #include <linux/libfdt.h>
+#include <linux/bitops.h>
 
 #include "../common/tdx-cfg-block.h"
 
@@ -28,22 +29,75 @@
 			 (SC_PAD_28FDSOI_DSE_DV_HIGH << PADRING_DSE_SHIFT) | \
 			 (SC_PAD_28FDSOI_PS_PU << PADRING_PULL_SHIFT))
 
+#define TDX_USER_FUSE_BLOCK1_A	276
+#define TDX_USER_FUSE_BLOCK1_B	277
+#define TDX_USER_FUSE_BLOCK2_A	278
+#define TDX_USER_FUSE_BLOCK2_B	279
+
 static iomux_cfg_t uart1_pads[] = {
 	SC_P_UART1_RX | MUX_PAD_CTRL(UART_PAD_CTRL),
 	SC_P_UART1_TX | MUX_PAD_CTRL(UART_PAD_CTRL),
 };
 
+struct tdx_user_fuses {
+	u16 pid4;
+	u16 vers;
+	u8 ramid;
+};
+
 static void setup_iomux_uart(void)
 {
 	imx8_iomux_setup_multiple_pads(uart1_pads, ARRAY_SIZE(uart1_pads));
 }
 
+static uint32_t do_get_tdx_user_fuse(int a, int b)
+{
+	sc_err_t sciErr;
+	u32 val_a = 0;
+	u32 val_b = 0;
+
+	sciErr = sc_misc_otp_fuse_read(-1, a, &val_a);
+	if (sciErr != SC_ERR_NONE) {
+		printf("Error reading out user fuse %d\n", a);
+		return 0;
+	}
+
+	sciErr = sc_misc_otp_fuse_read(-1, b, &val_b);
+	if (sciErr != SC_ERR_NONE) {
+		printf("Error reading out user fuse %d\n", b);
+		return 0;
+	}
+
+	return ((val_a & 0xffff) << 16) | (val_b & 0xffff);
+}
+
+static void get_tdx_user_fuse(struct tdx_user_fuses *tdxuserfuse)
+{
+	u32 fuse_block;
+
+	fuse_block = do_get_tdx_user_fuse(TDX_USER_FUSE_BLOCK2_A,
+					  TDX_USER_FUSE_BLOCK2_B);
+
+	/*
+	 * Fuse block 2 acts as a backup area, if this reads 0 we want to
+	 * use fuse block 1
+	 */
+	if (fuse_block == 0)
+		fuse_block = do_get_tdx_user_fuse(TDX_USER_FUSE_BLOCK1_A,
+						  TDX_USER_FUSE_BLOCK1_B);
+
+	tdxuserfuse->pid4 = (fuse_block >> 18) & GENMASK(13, 0);
+	tdxuserfuse->vers = (fuse_block >> 4) & GENMASK(13, 0);
+	tdxuserfuse->ramid = fuse_block & GENMASK(3, 0);
+}
+
 void board_mem_get_layout(u64 *phys_sdram_1_start,
 			  u64 *phys_sdram_1_size,
 			  u64 *phys_sdram_2_start,
 			  u64 *phys_sdram_2_size)
 {
 	u32 is_quadplus = 0, val = 0;
+	struct tdx_user_fuses tdxramfuses;
 	sc_err_t scierr = sc_misc_otp_fuse_read(-1, 6, &val);
 
 	if (scierr == SC_ERR_NONE) {
@@ -51,14 +105,33 @@
 		is_quadplus = ((val >> 4) & 0x3) != 0x0;
 	}
 
+	get_tdx_user_fuse(&tdxramfuses);
+
 	*phys_sdram_1_start = PHYS_SDRAM_1;
 	*phys_sdram_1_size = PHYS_SDRAM_1_SIZE;
 	*phys_sdram_2_start = PHYS_SDRAM_2;
-	if (is_quadplus)
-		/* Our QP based SKUs only have 2 GB RAM (PHYS_SDRAM_1_SIZE) */
+
+	switch (tdxramfuses.ramid) {
+	case 1:
+		*phys_sdram_2_size = SZ_2G;
+		break;
+	case 2:
 		*phys_sdram_2_size = 0x0UL;
-	else
-		*phys_sdram_2_size = PHYS_SDRAM_2_SIZE;
+		break;
+	case 3:
+		*phys_sdram_2_size = SZ_2G;
+		break;
+	case 4:
+		*phys_sdram_2_size = SZ_4G + SZ_2G;
+		break;
+	default:
+		if (is_quadplus)
+			/* Our QP based SKUs only have 2 GB RAM (PHYS_SDRAM_1_SIZE) */
+			*phys_sdram_2_size = 0x0UL;
+		else
+			*phys_sdram_2_size = PHYS_SDRAM_2_SIZE;
+		break;
+	}
 }
 
 int board_early_init_f(void)
diff --git a/board/toradex/common/tdx-cfg-block.c b/board/toradex/common/tdx-cfg-block.c
index 9c87289..6c8cf45 100644
--- a/board/toradex/common/tdx-cfg-block.c
+++ b/board/toradex/common/tdx-cfg-block.c
@@ -144,6 +144,7 @@
 	[64] = "Verdin iMX8M Plus Quad 2GB Wi-Fi / BT IT",
 	[65] = "Verdin iMX8M Plus QuadLite 1GB IT",
 	[66] = "Verdin iMX8M Plus Quad 8GB Wi-Fi / BT",
+	[67] = "Apalis iMX8 QuadMax 8GB Wi-Fi / BT IT",
 };
 
 const char * const toradex_carrier_boards[] = {
@@ -359,6 +360,7 @@
 	char *soc;
 	char it = 'n';
 	char wb = 'n';
+	char mem8g = 'n';
 	int len = 0;
 
 	/* Unknown module by default */
@@ -377,6 +379,14 @@
 	sprintf(message, "Does the module have Wi-Fi / Bluetooth? [y/N] ");
 	len = cli_readline(message);
 	wb = console_buffer[0];
+
+#if defined(CONFIG_TARGET_APALIS_IMX8)
+	if ((wb == 'y' || wb == 'Y') && (it == 'y' || it == 'Y')) {
+		sprintf(message, "Does your module have 8GB of RAM? [y/N] ");
+		len = cli_readline(message);
+		mem8g = console_buffer[0];
+	}
+#endif
 #endif
 
 	soc = env_get("soc");
@@ -430,8 +440,12 @@
 		tdx_hw_tag.prodid = COLIBRI_IMX7S;
 	else if (is_cpu_type(MXC_CPU_IMX8QM)) {
 		if (it == 'y' || it == 'Y') {
-			if (wb == 'y' || wb == 'Y')
-				tdx_hw_tag.prodid = APALIS_IMX8QM_WIFI_BT_IT;
+			if (wb == 'y' || wb == 'Y') {
+				if (mem8g == 'y' || mem8g == 'Y')
+					tdx_hw_tag.prodid = APALIS_IMX8QM_8GB_WIFI_BT_IT;
+				else
+					tdx_hw_tag.prodid = APALIS_IMX8QM_WIFI_BT_IT;
+			}
 			else
 				tdx_hw_tag.prodid = APALIS_IMX8QM_IT;
 		} else {
diff --git a/board/toradex/common/tdx-cfg-block.h b/board/toradex/common/tdx-cfg-block.h
index ddcf699..43e662e 100644
--- a/board/toradex/common/tdx-cfg-block.h
+++ b/board/toradex/common/tdx-cfg-block.h
@@ -87,6 +87,7 @@
 	VERDIN_IMX8MPQ_2GB_WIFI_BT_IT,
 	VERDIN_IMX8MPQL_IT, /* 65 */
 	VERDIN_IMX8MPQ_8GB_WIFI_BT,
+	APALIS_IMX8QM_8GB_WIFI_BT_IT,
 };
 
 enum {
diff --git a/configs/imx8mn_evk_defconfig b/configs/imx8mn_evk_defconfig
index c18c19f..52954b0 100644
--- a/configs/imx8mn_evk_defconfig
+++ b/configs/imx8mn_evk_defconfig
@@ -46,6 +46,9 @@
 CONFIG_CMD_GPIO=y
 CONFIG_CMD_I2C=y
 CONFIG_CMD_MMC=y
+CONFIG_CMD_DHCP=y
+CONFIG_CMD_MII=y
+CONFIG_CMD_PING=y
 CONFIG_CMD_CACHE=y
 CONFIG_CMD_REGULATOR=y
 CONFIG_CMD_EXT4_WRITE=y
@@ -70,7 +73,12 @@
 CONFIG_SPL_MMC_HS400_SUPPORT=y
 CONFIG_FSL_USDHC=y
 CONFIG_PHYLIB=y
+CONFIG_PHY_ATHEROS=y
 CONFIG_DM_ETH=y
+CONFIG_DM_ETH_PHY=y
+CONFIG_PHY_GIGE=y
+CONFIG_FEC_MXC=y
+CONFIG_MII=y
 CONFIG_PINCTRL=y
 CONFIG_SPL_PINCTRL=y
 CONFIG_PINCTRL_IMX8M=y
diff --git a/configs/mx6cuboxi_defconfig b/configs/mx6cuboxi_defconfig
index 1e2e332..46634a1 100644
--- a/configs/mx6cuboxi_defconfig
+++ b/configs/mx6cuboxi_defconfig
@@ -22,6 +22,7 @@
 CONFIG_AHCI=y
 CONFIG_DISTRO_DEFAULTS=y
 CONFIG_FIT=y
+CONFIG_OF_BOARD_SETUP=y
 CONFIG_BOOTCOMMAND="run findfdt; run finduuid; run distro_bootcmd"
 CONFIG_USE_PREBOOT=y
 CONFIG_PREBOOT="if hdmidet; then usb start; setenv stdin  serial,usbkbd; setenv stdout serial,vidconsole; setenv stderr serial,vidconsole; else setenv stdin  serial; setenv stdout serial; setenv stderr serial; fi;"
@@ -54,6 +55,7 @@
 CONFIG_SPL_SYS_I2C_LEGACY=y
 CONFIG_FSL_USDHC=y
 CONFIG_PHYLIB=y
+CONFIG_PHY_ADIN=y
 CONFIG_PHY_ATHEROS=y
 CONFIG_DM_ETH=y
 CONFIG_FEC_MXC=y
diff --git a/drivers/clk/imx/clk-imx8mp.c b/drivers/clk/imx/clk-imx8mp.c
index ac727b7..ffbc1d1 100644
--- a/drivers/clk/imx/clk-imx8mp.c
+++ b/drivers/clk/imx/clk-imx8mp.c
@@ -122,15 +122,15 @@
 					"sys_pll2_100m", "sys_pll1_800m",
 					"sys_pll2_500m", "clk_ext4", "audio_pll2_out" };
 
-static const char *imx8mp_ecspi1_sels[] = {"clock-osc_24m", "sys_pll2_200m", "sys_pll1_40m",
+static const char *imx8mp_ecspi1_sels[] = {"clock-osc-24m", "sys_pll2_200m", "sys_pll1_40m",
 						  "sys_pll1_160m", "sys_pll1_800m", "sys_pll3_out",
 						  "sys_pll2_250m", "audio_pll2_out", };
 
-static const char *imx8mp_ecspi2_sels[] = {"clock-osc_24m", "sys_pll2_200m", "sys_pll1_40m",
+static const char *imx8mp_ecspi2_sels[] = {"clock-osc-24m", "sys_pll2_200m", "sys_pll1_40m",
 						  "sys_pll1_160m", "sys_pll1_800m", "sys_pll3_out",
 						  "sys_pll2_250m", "audio_pll2_out", };
 
-static const char *imx8mp_ecspi3_sels[] = {"clock-osc_24m", "sys_pll2_200m", "sys_pll1_40m",
+static const char *imx8mp_ecspi3_sels[] = {"clock-osc-24m", "sys_pll2_200m", "sys_pll1_40m",
 						  "sys_pll1_160m", "sys_pll1_800m", "sys_pll3_out",
 						  "sys_pll2_250m", "audio_pll2_out", };
 
@@ -300,7 +300,7 @@
 	clk_dm(IMX8MP_CLK_UART2_ROOT, imx_clk_gate4("uart2_root_clk", "uart2", base + 0x44a0, 0));
 	clk_dm(IMX8MP_CLK_UART3_ROOT, imx_clk_gate4("uart3_root_clk", "uart3", base + 0x44b0, 0));
 	clk_dm(IMX8MP_CLK_UART4_ROOT, imx_clk_gate4("uart4_root_clk", "uart4", base + 0x44c0, 0));
-	clk_dm(IMX8MP_CLK_USB_ROOT, imx_clk_gate4("usb_root_clk", "osc_32k", base + 0x44d0, 0));
+	clk_dm(IMX8MP_CLK_USB_ROOT, imx_clk_gate4("usb_root_clk", "usb_core_ref", base + 0x44d0, 0));
 	clk_dm(IMX8MP_CLK_USB_PHY_ROOT, imx_clk_gate4("usb_phy_root_clk", "usb_phy_ref", base + 0x44f0, 0));
 	clk_dm(IMX8MP_CLK_USDHC1_ROOT, imx_clk_gate4("usdhc1_root_clk", "usdhc1", base + 0x4510, 0));
 	clk_dm(IMX8MP_CLK_USDHC2_ROOT, imx_clk_gate4("usdhc2_root_clk", "usdhc2", base + 0x4520, 0));
diff --git a/drivers/net/phy/adin.c b/drivers/net/phy/adin.c
index cff841a..a5bfd96 100644
--- a/drivers/net/phy/adin.c
+++ b/drivers/net/phy/adin.c
@@ -4,6 +4,7 @@
  *
  * Copyright 2019 Analog Devices Inc.
  * Copyright 2022 Variscite Ltd.
+ * Copyright 2022 Josua Mayer <josua@solid-run.com>
  */
 #include <common.h>
 #include <phy.h>
@@ -13,6 +14,16 @@
 #define PHY_ID_ADIN1300				0x0283bc30
 #define ADIN1300_EXT_REG_PTR			0x10
 #define ADIN1300_EXT_REG_DATA			0x11
+
+#define ADIN1300_GE_CLK_CFG_REG			0xff1f
+#define   ADIN1300_GE_CLK_CFG_MASK		GENMASK(5, 0)
+#define   ADIN1300_GE_CLK_CFG_RCVR_125		BIT(5)
+#define   ADIN1300_GE_CLK_CFG_FREE_125		BIT(4)
+#define   ADIN1300_GE_CLK_CFG_REF_EN		BIT(3)
+#define   ADIN1300_GE_CLK_CFG_HRT_RCVR		BIT(2)
+#define   ADIN1300_GE_CLK_CFG_HRT_FREE		BIT(1)
+#define   ADIN1300_GE_CLK_CFG_25		BIT(0)
+
 #define ADIN1300_GE_RGMII_CFG			0xff23
 #define ADIN1300_GE_RGMII_RX_MSK		GENMASK(8, 6)
 #define ADIN1300_GE_RGMII_RX_SEL(x)		\
@@ -100,27 +111,27 @@
  * The function gets phy-mode string from property 'adi,phy-mode-override'
  * and return its index in phy_interface_strings table, or -1 in error case.
  */
-int adin_get_phy_mode_override(struct phy_device *phydev)
+phy_interface_t adin_get_phy_mode_override(struct phy_device *phydev)
 {
 	ofnode node = phy_get_ofnode(phydev);
 	const char *phy_mode_override;
 	const char *prop_phy_mode_override = "adi,phy-mode-override";
-	int override_interface;
+	int i;
 
 	phy_mode_override = ofnode_read_string(node, prop_phy_mode_override);
 	if (!phy_mode_override)
-		return -ENODEV;
+		return PHY_INTERFACE_MODE_NA;
 
 	debug("%s: %s = '%s'\n",
 	      __func__, prop_phy_mode_override, phy_mode_override);
 
-	override_interface = phy_get_interface_by_name(phy_mode_override);
+	for (i = 0; i < PHY_INTERFACE_MODE_MAX; i++)
+		if (!strcmp(phy_mode_override, phy_interface_strings[i]))
+			return (phy_interface_t) i;
 
-	if (override_interface < 0)
-		printf("%s: %s = '%s' is not valid\n",
-		       __func__, prop_phy_mode_override, phy_mode_override);
+	printf("%s: Invalid PHY interface '%s'\n", __func__, phy_mode_override);
 
-	return override_interface;
+	return PHY_INTERFACE_MODE_NA;
 }
 
 static u16 adin_ext_read(struct phy_device *phydev, const u32 regnum)
@@ -144,14 +155,41 @@
 	return phy_write(phydev, MDIO_DEVAD_NONE, ADIN1300_EXT_REG_DATA, val);
 }
 
+static int adin_config_clk_out(struct phy_device *phydev)
+{
+	ofnode node = phy_get_ofnode(phydev);
+	const char *val = NULL;
+	u8 sel = 0;
+
+	val = ofnode_read_string(node, "adi,phy-output-clock");
+	if (!val) {
+		/* property not present, do not enable GP_CLK pin */
+	} else if (strcmp(val, "25mhz-reference") == 0) {
+		sel |= ADIN1300_GE_CLK_CFG_25;
+	} else if (strcmp(val, "125mhz-free-running") == 0) {
+		sel |= ADIN1300_GE_CLK_CFG_FREE_125;
+	} else if (strcmp(val, "adaptive-free-running") == 0) {
+		sel |= ADIN1300_GE_CLK_CFG_HRT_FREE;
+	} else {
+		pr_err("%s: invalid adi,phy-output-clock\n", __func__);
+		return -EINVAL;
+	}
+
+	if (ofnode_read_bool(node, "adi,phy-output-reference-clock"))
+		sel |= ADIN1300_GE_CLK_CFG_REF_EN;
+
+	return adin_ext_write(phydev, ADIN1300_GE_CLK_CFG_REG,
+			      ADIN1300_GE_CLK_CFG_MASK & sel);
+}
+
 static int adin_config_rgmii_mode(struct phy_device *phydev)
 {
 	u16 reg_val;
 	u32 val;
-	int phy_mode_override = adin_get_phy_mode_override(phydev);
+	phy_interface_t phy_mode_override = adin_get_phy_mode_override(phydev);
 
-	if (phy_mode_override >= 0) {
-		phydev->interface = (phy_interface_t) phy_mode_override;
+	if (phy_mode_override != PHY_INTERFACE_MODE_NA) {
+		phydev->interface = phy_mode_override;
 	}
 
 	reg_val = adin_ext_read(phydev, ADIN1300_GE_RGMII_CFG);
@@ -202,6 +240,10 @@
 
 	printf("ADIN1300 PHY detected at addr %d\n", phydev->addr);
 
+	ret = adin_config_clk_out(phydev);
+	if (ret < 0)
+		return ret;
+
 	ret = adin_config_rgmii_mode(phydev);
 
 	if (ret < 0)
diff --git a/drivers/spi/nxp_fspi.c b/drivers/spi/nxp_fspi.c
index 607c953..579d6ba 100644
--- a/drivers/spi/nxp_fspi.c
+++ b/drivers/spi/nxp_fspi.c
@@ -866,9 +866,6 @@
 	u32 reg;
 
 #if CONFIG_IS_ENABLED(CLK)
-	/* disable and unprepare clock to avoid glitch pass to controller */
-	nxp_fspi_clk_disable_unprep(f);
-
 	/* the default frequency, we will change it later if necessary. */
 	ret = clk_set_rate(&f->clk, 20000000);
 	if (ret < 0)
diff --git a/include/configs/verdin-imx8mm.h b/include/configs/verdin-imx8mm.h
index cd950ad..558b781 100644
--- a/include/configs/verdin-imx8mm.h
+++ b/include/configs/verdin-imx8mm.h
@@ -58,8 +58,8 @@
 	"fdt_board=dev\0" \
 	"initrd_addr=0x43800000\0" \
 	"initrd_high=0xffffffffffffffff\0" \
-	"setup=setenv setupargs console=${console},${baudrate} " \
-		"console=tty1 consoleblank=0 earlycon\0" \
+	"setup=setenv setupargs console=tty1 console=${console},${baudrate} " \
+		"consoleblank=0 earlycon\0" \
 	"update_uboot=askenv confirm Did you load flash.bin (y/N)?; " \
 		"if test \"$confirm\" = \"y\"; then " \
 		"setexpr blkcnt ${filesize} + 0x1ff && setexpr blkcnt " \
diff --git a/include/configs/verdin-imx8mp.h b/include/configs/verdin-imx8mp.h
index 470f64d..52fa2be 100644
--- a/include/configs/verdin-imx8mp.h
+++ b/include/configs/verdin-imx8mp.h
@@ -75,7 +75,7 @@
 	"fdt_board=dev\0" \
 	"initrd_addr=0x43800000\0" \
 	"initrd_high=0xffffffffffffffff\0" \
-	"setup=setenv setupargs console=${console},${baudrate} console=tty1 " \
+	"setup=setenv setupargs console=tty1 console=${console},${baudrate} " \
 		"consoleblank=0 earlycon\0" \
 	"update_uboot=askenv confirm Did you load flash.bin (y/N)?; " \
 		"if test \"$confirm\" = \"y\"; then " \