Merge branch 'master' of https://source.denx.de/u-boot/custodians/u-boot-marvell

- kirkwood: Add Pogoplug-V4 support (Tony)
- kirkwood: GoFlex Home : Use Marvell PHY driver (Tony)
- Another set of kwboot improvements (Pali)
- Minor misc stuff
diff --git a/arch/arm/dts/Makefile b/arch/arm/dts/Makefile
index ce33202..5d45d19 100644
--- a/arch/arm/dts/Makefile
+++ b/arch/arm/dts/Makefile
@@ -71,6 +71,7 @@
 	kirkwood-openrd-client.dtb \
 	kirkwood-openrd-ultimate.dtb \
 	kirkwood-pogo_e02.dtb \
+	kirkwood-pogoplug-series-4.dtb \
 	kirkwood-sheevaplug.dtb
 
 dtb-$(CONFIG_MACH_S900) += \
diff --git a/arch/arm/dts/kirkwood-pogoplug-series-4.dts b/arch/arm/dts/kirkwood-pogoplug-series-4.dts
new file mode 100644
index 0000000..5aa4669
--- /dev/null
+++ b/arch/arm/dts/kirkwood-pogoplug-series-4.dts
@@ -0,0 +1,180 @@
+// SPDX-License-Identifier: GPL-2.0
+/*
+ * kirkwood-pogoplug-series-4.dts - Device tree file for PogoPlug Series 4
+ * inspired by the board files made by Kevin Mihelich for ArchLinux,
+ * and their DTS file.
+ *
+ * Copyright (C) 2015 Linus Walleij <linus.walleij@linaro.org>
+ */
+
+/dts-v1/;
+
+#include "kirkwood.dtsi"
+#include "kirkwood-6192.dtsi"
+#include <dt-bindings/input/linux-event-codes.h>
+
+/ {
+	model = "Cloud Engines PogoPlug Series 4";
+	compatible = "cloudengines,pogoplugv4", "marvell,kirkwood-88f6192",
+		     "marvell,kirkwood";
+
+	memory {
+		device_type = "memory";
+		reg = <0x00000000 0x08000000>;
+	};
+
+	chosen {
+		stdout-path = "uart0:115200n8";
+	};
+
+	gpio_keys {
+		compatible = "gpio-keys";
+		#address-cells = <1>;
+		#size-cells = <0>;
+		pinctrl-0 = <&pmx_button_eject>;
+		pinctrl-names = "default";
+
+		eject {
+			debounce-interval = <50>;
+			wakeup-source;
+			linux,code = <KEY_EJECTCD>;
+			label = "Eject Button";
+			gpios = <&gpio0 29 GPIO_ACTIVE_LOW>;
+		};
+	};
+
+	gpio-leds {
+		compatible = "gpio-leds";
+		pinctrl-0 = <&pmx_led_green &pmx_led_red>;
+		pinctrl-names = "default";
+
+		health {
+			label = "pogoplugv4:green:health";
+			gpios = <&gpio0 22 GPIO_ACTIVE_LOW>;
+			default-state = "on";
+		};
+		fault {
+			label = "pogoplugv4:red:fault";
+			gpios = <&gpio0 24 GPIO_ACTIVE_LOW>;
+		};
+	};
+};
+
+&pinctrl {
+	pmx_sata0: pmx-sata0 {
+		marvell,pins = "mpp21";
+		marvell,function = "sata0";
+	};
+
+	pmx_sata1: pmx-sata1 {
+		marvell,pins = "mpp20";
+		marvell,function = "sata1";
+	};
+
+	pmx_sdio_cd: pmx-sdio-cd {
+		marvell,pins = "mpp27";
+		marvell,function = "gpio";
+	};
+
+	pmx_sdio_wp: pmx-sdio-wp {
+		marvell,pins = "mpp28";
+		marvell,function = "gpio";
+	};
+
+	pmx_button_eject: pmx-button-eject {
+		marvell,pins = "mpp29";
+		marvell,function = "gpio";
+	};
+
+	pmx_led_green: pmx-led-green {
+		marvell,pins = "mpp22";
+		marvell,function = "gpio";
+	};
+
+	pmx_led_red: pmx-led-red {
+		marvell,pins = "mpp24";
+		marvell,function = "gpio";
+	};
+};
+
+&uart0 {
+	status = "okay";
+};
+
+/*
+ * This PCIE controller has a USB 3.0 XHCI controller at 1,0
+ */
+&pciec {
+	status = "okay";
+};
+
+&pcie0 {
+	status = "okay";
+};
+
+&sata {
+	status = "okay";
+	pinctrl-0 = <&pmx_sata0 &pmx_sata1>;
+	pinctrl-names = "default";
+	nr-ports = <1>;
+};
+
+&sdio {
+	status = "okay";
+	pinctrl-0 = <&pmx_sdio &pmx_sdio_cd &pmx_sdio_wp>;
+	pinctrl-names = "default";
+	cd-gpios = <&gpio0 27 GPIO_ACTIVE_LOW>;
+	wp-gpios = <&gpio0 28 GPIO_ACTIVE_HIGH>;
+};
+
+&nand {
+	/* 128 MiB of NAND flash */
+	chip-delay = <40>;
+	status = "okay";
+	partitions {
+		compatible = "fixed-partitions";
+		#address-cells = <1>;
+		#size-cells = <1>;
+
+		partition@0 {
+			label = "u-boot";
+			reg = <0x00000000 0x200000>;
+			read-only;
+		};
+
+		partition@200000 {
+			label = "uImage";
+			reg = <0x00200000 0x300000>;
+		};
+
+		partition@500000 {
+			label = "uImage2";
+			reg = <0x00500000 0x300000>;
+		};
+
+		partition@800000 {
+			label = "failsafe";
+			reg = <0x00800000 0x800000>;
+		};
+
+		partition@1000000 {
+			label = "root";
+			reg = <0x01000000 0x7000000>;
+		};
+	};
+};
+
+&mdio {
+	status = "okay";
+
+	ethphy0: ethernet-phy@0 {
+		reg = <0>;
+	};
+};
+
+&eth0 {
+	status = "okay";
+	ethernet0-port@0 {
+		phy-handle = <&ethphy0>;
+	};
+};
diff --git a/arch/arm/mach-kirkwood/Kconfig b/arch/arm/mach-kirkwood/Kconfig
index c060cc8..382b836 100644
--- a/arch/arm/mach-kirkwood/Kconfig
+++ b/arch/arm/mach-kirkwood/Kconfig
@@ -51,6 +51,11 @@
 	select FEROCEON_88FR131
 	select KW88F6281
 
+config TARGET_POGO_V4
+	bool "Pogoplug V4 Board"
+	select FEROCEON_88FR131
+	select KW88F6192
+
 config TARGET_DNS325
 	bool "dns325 Board"
 	select FEROCEON_88FR131
@@ -123,6 +128,7 @@
 source "board/Marvell/sheevaplug/Kconfig"
 source "board/buffalo/lsxl/Kconfig"
 source "board/cloudengines/pogo_e02/Kconfig"
+source "board/cloudengines/pogo_v4/Kconfig"
 source "board/d-link/dns325/Kconfig"
 source "board/iomega/iconnect/Kconfig"
 source "board/keymile/Kconfig"
diff --git a/board/Marvell/mvebu_armada-37xx/board.c b/board/Marvell/mvebu_armada-37xx/board.c
index d7b6eca..6bfec0c 100644
--- a/board/Marvell/mvebu_armada-37xx/board.c
+++ b/board/Marvell/mvebu_armada-37xx/board.c
@@ -59,11 +59,11 @@
  * Memory Controller Registers
  *
  * Assembled based on public information:
- * https://gitlab.nic.cz/turris/mox-boot-builder/-/blob/master/wtmi/main.c#L332-336
+ * https://gitlab.nic.cz/turris/mox-boot-builder/-/blob/v2020.11.26/wtmi/main.c#L332-336
  * https://github.com/MarvellEmbeddedProcessors/mv-ddr-marvell/blob/mv_ddr-armada-18.12/drivers/mv_ddr_mc6.h#L309-L332
  *
  * And checked against the written register values for the various topologies:
- * https://github.com/MarvellEmbeddedProcessors/mv-ddr-marvell/blob/mv_ddr-armada-atf-mainline/a3700/mv_ddr_tim.h
+ * https://github.com/MarvellEmbeddedProcessors/mv-ddr-marvell/blob/master/a3700/mv_ddr_tim.h
  */
 #define A3700_CH0_MC_CTRL2_REG		MVEBU_REGISTER(0x002c4)
 #define A3700_MC_CTRL2_SDRAM_TYPE_MASK	0xf
diff --git a/board/Seagate/goflexhome/goflexhome.c b/board/Seagate/goflexhome/goflexhome.c
index 52be64f..caea89c 100644
--- a/board/Seagate/goflexhome/goflexhome.c
+++ b/board/Seagate/goflexhome/goflexhome.c
@@ -1,10 +1,7 @@
 // SPDX-License-Identifier: GPL-2.0+
 /*
- * Copyright (C) 2021
- * Tony Dinh <mibodhi@gmail.com>
- * Suriyan Ramasami <suriyan.r@gmail.com>
- *
- * Copyright (C) 2013 Suriyan Ramasami <suriyan.r@gmail.com>
+ * Copyright (C) 2021-2022 Tony Dinh <mibodhi@gmail.com>
+ * Copyright (C) 2013-2021 Suriyan Ramasami <suriyan.r@gmail.com>
  *
  * Based on dockstar.c originally written by
  * Copyright (C) 2010  Eric C. Cooper <ecc@cmu.edu>
@@ -18,14 +15,14 @@
 #include <common.h>
 #include <bootstage.h>
 #include <init.h>
-#include <miiphy.h>
-#include <net.h>
+#include <netdev.h>
 #include <asm/global_data.h>
 #include <asm/mach-types.h>
 #include <asm/arch/soc.h>
 #include <asm/arch/mpp.h>
 #include <asm/arch/cpu.h>
 #include <asm/io.h>
+#include <linux/bitops.h>
 
 DECLARE_GLOBAL_DATA_PTR;
 
@@ -98,6 +95,11 @@
 	return 0;
 }
 
+int board_eth_init(struct bd_info *bis)
+{
+	return cpu_eth_init(bis);
+}
+
 int board_init(void)
 {
 	/*
@@ -111,73 +113,9 @@
 	return 0;
 }
 
-static int fdt_get_phy_addr(const char *path)
-{
-	const void *fdt = gd->fdt_blob;
-	const u32 *reg;
-	const u32 *val;
-	int node, phandle, addr;
-
-	/* Find the node by its full path */
-	node = fdt_path_offset(fdt, path);
-	if (node >= 0) {
-		/* Look up phy-handle */
-		val = fdt_getprop(fdt, node, "phy-handle", NULL);
-		if (val) {
-			phandle = fdt32_to_cpu(*val);
-			if (!phandle)
-				return -1;
-			/* Follow it to its node */
-			node = fdt_node_offset_by_phandle(fdt, phandle);
-			if (node) {
-				/* Look up reg */
-				reg = fdt_getprop(fdt, node, "reg", NULL);
-				if (reg) {
-					addr = fdt32_to_cpu(*reg);
-					return addr;
-				}
-			}
-		}
-	}
-	return -1;
-}
-
-#ifdef CONFIG_RESET_PHY_R
-/* Configure and enable MV88E1116 PHY */
-void reset_phy(void)
-{
-	u16 reg;
-	int phyaddr;
-	char *name = "ethernet-controller@72000";
-	char *eth0_path = "/ocp@f1000000/ethernet-controller@72000/ethernet0-port@0";
-
-	if (miiphy_set_current_dev(name))
-		return;
-
-	phyaddr = fdt_get_phy_addr(eth0_path);
-	if (phyaddr < 0)
-		return;
-
-	/*
-	 * Enable RGMII delay on Tx and Rx for CPU port
-	 * Ref: sec 4.7.2 of chip datasheet
-	 */
-	miiphy_write(name, phyaddr, MV88E1116_PGADR_REG, 2);
-	miiphy_read(name, phyaddr, MV88E1116_MAC_CTRL_REG, &reg);
-	reg |= (MV88E1116_RGMII_RXTM_CTRL | MV88E1116_RGMII_TXTM_CTRL);
-	miiphy_write(name, phyaddr, MV88E1116_MAC_CTRL_REG, reg);
-	miiphy_write(name, phyaddr, MV88E1116_PGADR_REG, 0);
-
-	/* reset the phy */
-	miiphy_reset(name, phyaddr);
-
-	printf("88E1116 Initialized on %s\n", name);
-}
-#endif /* CONFIG_RESET_PHY_R */
-
 #if CONFIG_IS_ENABLED(BOOTSTAGE)
-#define GREEN_LED	(1 << 14)
-#define ORANGE_LED	(1 << 15)
+#define GREEN_LED	BIT(14)
+#define ORANGE_LED	BIT(15)
 #define BOTH_LEDS	(GREEN_LED | ORANGE_LED)
 #define NEITHER_LED	0
 
diff --git a/board/cloudengines/pogo_v4/Kconfig b/board/cloudengines/pogo_v4/Kconfig
new file mode 100644
index 0000000..db3b76b
--- /dev/null
+++ b/board/cloudengines/pogo_v4/Kconfig
@@ -0,0 +1,16 @@
+# SPDX-License-Identifier: GPL-2.0+
+#
+# (C) Copyright 2014-2021 Tony Dinh <mibodhi@gmail.com>
+#
+if TARGET_POGO_V4
+
+config SYS_BOARD
+	default "pogo_v4"
+
+config SYS_VENDOR
+	default "cloudengines"
+
+config SYS_CONFIG_NAME
+	default "pogo_v4"
+
+endif
diff --git a/board/cloudengines/pogo_v4/MAINTAINERS b/board/cloudengines/pogo_v4/MAINTAINERS
new file mode 100644
index 0000000..35fd785
--- /dev/null
+++ b/board/cloudengines/pogo_v4/MAINTAINERS
@@ -0,0 +1,6 @@
+POGO_V4 BOARD
+M:	Tony Dinh <mibodhi@gmail.com>
+S:	Maintained
+F:	board/cloudengines/pogo_v4/
+F:	include/configs/pogo_v4.h
+F:	configs/pogo_v4_defconfig
diff --git a/board/cloudengines/pogo_v4/Makefile b/board/cloudengines/pogo_v4/Makefile
new file mode 100644
index 0000000..511bf5f
--- /dev/null
+++ b/board/cloudengines/pogo_v4/Makefile
@@ -0,0 +1,10 @@
+# SPDX-License-Identifier: GPL-2.0+
+#
+# (C) Copyright 2014-2021 Tony Dinh <mibodhi@gmail.com>
+#
+# Based on
+# Marvell Semiconductor <www.marvell.com>
+# Written-by: Prafulla Wadaskar <prafulla@marvell.com>
+#
+
+obj-y	:= pogo_v4.o
diff --git a/board/cloudengines/pogo_v4/kwbimage.cfg b/board/cloudengines/pogo_v4/kwbimage.cfg
new file mode 100644
index 0000000..f6294fe
--- /dev/null
+++ b/board/cloudengines/pogo_v4/kwbimage.cfg
@@ -0,0 +1,148 @@
+# SPDX-License-Identifier: GPL-2.0+
+#
+# Copyright (C) 2012
+# David Purdy <david.c.purdy@gmail.com>
+#
+# Based on Kirkwood support:
+# (C) Copyright 2009
+# Marvell Semiconductor <www.marvell.com>
+# Written-by: Prafulla Wadaskar <prafulla <at> marvell.com>
+
+# Boot Media configurations   (DONE)
+BOOT_FROM	nand
+NAND_ECC_MODE	default
+NAND_PAGE_SIZE	0x0800
+
+# SOC registers configuration using bootrom header extension
+# Maximum KWBIMAGE_MAX_CONFIG configurations allowed
+
+# Configure RGMII-0 interface pad voltage to 1.8V (SHOULD BE SAME)
+DATA 0xffd100e0 0x1b1b1b9b
+
+#Dram initalization for SINGLE x16 CL=3 @ 200MHz   (need CL=3 @ 200MHz?)
+DATA 0xffd01400 0x43000618	# DDR Configuration register
+# bit13-0:  0x200 (200 DDR2 clks refresh rate)
+# bit23-14: zero
+# bit24: 1= enable exit self refresh mode on DDR access
+# bit25: 1 required
+# bit29-26: zero
+# bit31-30: 01
+
+DATA 0xffd01404 0x34143000	# DDR Controller Control Low
+# bit 4:    0=addr/cmd in smame cycle
+# bit 5:    0=clk is driven during self refresh, we don't care for APX
+# bit 6:    0=use recommended falling edge of clk for addr/cmd
+# bit14:    0=input buffer always powered up
+# bit18:    1=cpu lock transaction enabled
+# bit23-20: 3=recommended value for CL=3 and STARTBURST_DEL disabled bit31=0
+# bit27-24: 6= CL+3, STARTBURST sample stages, for freqs 400MHz, unbuffered DIMM
+# bit30-28: 3 required
+# bit31:    0=no additional STARTBURST delay
+
+DATA 0xffd01408 0x11012227	# DDR Timing (Low) (active cycles value +1)
+# bit3-0:   TRAS lsbs
+# bit7-4:   TRCD
+# bit11- 8: TRP
+# bit15-12: TWR
+# bit19-16: TWTR
+# bit20:    TRAS msb
+# bit23-21: 0x0
+# bit27-24: TRRD
+# bit31-28: TRTP
+
+DATA 0xffd0140c 0x00000819	#  DDR Timing (High)
+# bit6-0:   TRFC
+# bit8-7:   TR2R
+# bit10-9:  TR2W
+# bit12-11: TW2W
+# bit31-13: zero required
+
+DATA 0xffd01410 0x00000001	#  DDR Address Control  (changed to Dockstar vals)
+# bit1-0:   00, Cs0width=x16
+# bit3-2:   10, Cs0size=512Mb
+# bit5-4:   00, Cs2width=nonexistent
+# bit7-6:   00, Cs1size =nonexistent
+# bit9-8:   00, Cs2width=nonexistent
+# bit11-10: 00, Cs2size =nonexistent
+# bit13-12: 00, Cs3width=nonexistent
+# bit15-14: 00, Cs3size =nonexistent
+# bit16:    0,  Cs0AddrSel
+# bit17:    0,  Cs1AddrSel
+# bit18:    0,  Cs2AddrSel
+# bit19:    0,  Cs3AddrSel
+# bit31-20: 0 required
+
+DATA 0xffd01414 0x00000000	#  DDR Open Pages Control
+# bit0:    0,  OpenPage enabled
+# bit31-1: 0 required
+
+DATA 0xffd01418 0x00000000	#  DDR Operation
+# bit3-0:   0x0, DDR cmd
+# bit31-4:  0 required
+
+DATA 0xffd0141c 0x00000632	#  DDR Mode
+# bit2-0:   2, BurstLen=2 required
+# bit3:     0, BurstType=0 required
+# bit6-4:   4, CL=5				(<===== change to CL=3 ?)
+# bit7:     0, TestMode=0 normal
+# bit8:     0, DLL reset=0 normal
+# bit11-9:  6, auto-precharge write recovery ????????????
+# bit12:    0, PD must be zero
+# bit31-13: 0 required
+
+DATA 0xffd01420 0x00000040	#  DDR Extended Mode
+# bit0:    0,  DDR DLL enabled
+# bit1:    0,  DDR drive strenght normal
+# bit2:    0,  DDR ODT control lsd (disabled)
+# bit5-3:  000, required
+# bit6:    1,  DDR ODT control msb, (disabled)
+# bit9-7:  000, required
+# bit10:   0,  differential DQS enabled
+# bit11:   0, required
+# bit12:   0, DDR output buffer enabled
+# bit31-13: 0 required
+
+DATA 0xffd01424 0x0000F07F	#  DDR Controller Control High
+# bit2-0:  111, required
+# bit3  :  1  , MBUS Burst Chop disabled
+# bit6-4:  111, required
+# bit7  :  0
+# bit8  :  0  , no sample stage
+# bit9  :  0  , no half clock cycle addition to dataout
+# bit10 :  0  , 1/4 clock cycle skew enabled for addr/ctl signals
+# bit11 :  0  , 1/4 clock cycle skew disabled for write mesh
+# bit15-12: 1111 required
+# bit31-16: 0    required
+
+DATA 0xffd01428 0x00085520	# DDR2 ODT Read Timing (default values)
+DATA 0xffd0147c 0x00008552	# DDR2 ODT Write Timing (default values)
+
+DATA 0xFFD01500 0x00000000	# CS[0]n Base address to 0x0
+DATA 0xFFD01504 0x07FFFFF1	# CS[0]n Size
+# bit0:    1,  Window enabled
+# bit1:    0,  Write Protect disabled
+# bit3-2:  00, CS0 hit selected
+# bit23-4: ones, required
+# bit31-24: 0x07, Size (i.e. 128MB)
+
+DATA 0xFFD0150C 0x00000000	# CS[1]n Size, window disabled
+DATA 0xFFD01514 0x00000000	# CS[2]n Size, window disabled
+DATA 0xFFD0151C 0x00000000	# CS[3]n Size, window disabled
+
+DATA 0xffd01494 0x00030000	#  DDR ODT Control (Low)		 (DONE)
+# bit3-0:  2, ODT0Rd, MODT[0] asserted during read from DRAM CS1
+# bit7-4:  1, ODT0Rd, MODT[0] asserted during read from DRAM CS0
+# bit19-16:2, ODT0Wr, MODT[0] asserted during write to DRAM CS1
+# bit23-20:1, ODT0Wr, MODT[0] asserted during write to DRAM CS0
+
+DATA 0xffd01498 0x00000000	#  DDR ODT Control (High)  (DONE)
+# bit1-0:  00, ODT0 controlled by ODT Control (low) register above
+# bit3-2:  01, ODT1 active NEVER!
+# bit31-4: zero, required
+
+DATA 0xffd0149c 0x0000e803	# CPU ODT Control	 (DONE)
+DATA 0xffd01480 0x00000001	# DDR Initialization Control	 (DONE)
+#bit0=1, enable DDR init upon this register write
+
+# End of Header extension
+DATA 0x0 0x0
diff --git a/board/cloudengines/pogo_v4/pogo_v4.c b/board/cloudengines/pogo_v4/pogo_v4.c
new file mode 100644
index 0000000..61ce0d5
--- /dev/null
+++ b/board/cloudengines/pogo_v4/pogo_v4.c
@@ -0,0 +1,148 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright (C) 2014-2022 Tony Dinh <mibodhi@gmail.com>
+ *
+ * Based on
+ * Copyright (C) 2012 David Purdy <david.c.purdy@gmail.com>
+ *
+ * Based on Kirkwood support:
+ * (C) Copyright 2009
+ * Marvell Semiconductor <www.marvell.com>
+ * Written-by: Prafulla Wadaskar <prafulla@marvell.com>
+ */
+
+#include <common.h>
+#include <netdev.h>
+#include <asm/arch/cpu.h>
+#include <asm/arch/soc.h>
+#include <asm/arch/mpp.h>
+#include <asm/io.h>
+#include <asm/arch/gpio.h>
+#include <asm/mach-types.h>
+#include <bootstage.h>
+#include <command.h>
+#include <init.h>
+#include <linux/bitops.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+/* GPIO configuration */
+#define POGO_V4_OE_LOW				(~(0))
+#define POGO_V4_OE_HIGH				(~(0))
+#define POGO_V4_OE_VAL_LOW			BIT(29)
+#define POGO_V4_OE_VAL_HIGH			0
+
+/* button */
+#define BTN_EJECT				29
+
+int board_early_init_f(void)
+{
+	/*
+	 * default gpio configuration
+	 * There are maximum 64 gpios controlled through 2 sets of registers
+	 * the  below configuration configures mainly initial LED status
+	 */
+	mvebu_config_gpio(POGO_V4_OE_VAL_LOW,
+			  POGO_V4_OE_VAL_HIGH,
+			  POGO_V4_OE_LOW, POGO_V4_OE_HIGH);
+
+	/* Multi-Purpose Pins Functionality configuration */
+	u32 kwmpp_config[] = {
+		MPP0_NF_IO2,
+		MPP1_NF_IO3,
+		MPP2_NF_IO4,
+		MPP3_NF_IO5,
+		MPP4_NF_IO6,
+		MPP5_NF_IO7,
+		MPP6_SYSRST_OUTn,
+		MPP7_GPO,
+		MPP8_TW_SDA,
+		MPP9_TW_SCK,
+		MPP10_UART0_TXD,
+		MPP11_UART0_RXD,
+		MPP12_SD_CLK,
+		MPP13_SD_CMD,
+		MPP14_SD_D0,
+		MPP15_SD_D1,
+		MPP16_SD_D2,
+		MPP17_SD_D3,
+		MPP18_NF_IO0,
+		MPP19_NF_IO1,
+		MPP20_SATA1_ACTn,
+		MPP21_SATA0_ACTn,
+		MPP22_GPIO,	/* Green LED */
+		MPP23_GPIO,
+		MPP24_GPIO,	/* Red LED */
+		MPP25_GPIO,
+		MPP26_GPIO,
+		MPP27_GPIO,
+		MPP28_GPIO,
+		MPP29_GPIO,	/* Eject button */
+		MPP30_GPIO,
+		MPP31_GPIO,
+		MPP32_GPIO,
+		MPP33_GPIO,
+		MPP34_GPIO,
+		MPP35_GPIO,	/* FR6192 has only 36 GPIOs */
+		0
+	};
+	kirkwood_mpp_conf(kwmpp_config, NULL);
+
+	return 0;
+}
+
+int board_eth_init(struct bd_info *bis)
+{
+	return cpu_eth_init(bis);
+}
+
+int board_late_init(void)
+{
+	/* Do late init to ensure successful enumeration of XHCI devices */
+	pci_init();
+	return 0;
+}
+
+int board_init(void)
+{
+	/* Boot parameters address */
+	gd->bd->bi_boot_params = mvebu_sdram_bar(0) + 0x100;
+
+	return 0;
+}
+
+#if CONFIG_IS_ENABLED(BOOTSTAGE)
+#define GREEN_LED	BIT(22)
+#define RED_LED		BIT(24)
+#define BOTH_LEDS	(GREEN_LED | RED_LED)
+#define NEITHER_LED	0
+
+static void set_leds(u32 leds, u32 blinking)
+{
+	struct kwgpio_registers *r;
+	u32 oe;
+	u32 bl;
+
+	r = (struct kwgpio_registers *)MVEBU_GPIO0_BASE;
+	oe = readl(&r->oe) | BOTH_LEDS;
+	writel(oe & ~leds, &r->oe);	/* active low */
+	bl = readl(&r->blink_en) & ~BOTH_LEDS;
+	writel(bl | blinking, &r->blink_en);
+}
+
+void show_boot_progress(int val)
+{
+	switch (val) {
+	case BOOTSTAGE_ID_RUN_OS:		/* booting Linux */
+		set_leds(BOTH_LEDS, NEITHER_LED);
+		break;
+	case BOOTSTAGE_ID_NET_ETH_START:	/* Ethernet initialization */
+		set_leds(GREEN_LED, GREEN_LED);
+		break;
+	default:
+		if (val < 0)	/* error */
+			set_leds(RED_LED, RED_LED);
+		break;
+	}
+}
+#endif
diff --git a/configs/goflexhome_defconfig b/configs/goflexhome_defconfig
index ec8b739..e6eb00a 100644
--- a/configs/goflexhome_defconfig
+++ b/configs/goflexhome_defconfig
@@ -2,6 +2,7 @@
 CONFIG_SKIP_LOWLEVEL_INIT=y
 CONFIG_SYS_DCACHE_OFF=y
 CONFIG_ARCH_CPU_INIT=y
+CONFIG_SYS_THUMB_BUILD=y
 CONFIG_ARCH_KIRKWOOD=y
 CONFIG_SYS_KWD_CONFIG="board/Seagate/goflexhome/kwbimage.cfg"
 CONFIG_SYS_TEXT_BASE=0x600000
@@ -47,6 +48,7 @@
 # CONFIG_MMC is not set
 CONFIG_MTD=y
 CONFIG_MTD_RAW_NAND=y
+CONFIG_PHY_MARVELL=y
 CONFIG_DM_ETH=y
 CONFIG_MVGBE=y
 CONFIG_MII=y
diff --git a/configs/pogo_v4_defconfig b/configs/pogo_v4_defconfig
new file mode 100644
index 0000000..1cf409c
--- /dev/null
+++ b/configs/pogo_v4_defconfig
@@ -0,0 +1,80 @@
+CONFIG_ARM=y
+CONFIG_SKIP_LOWLEVEL_INIT=y
+CONFIG_SYS_DCACHE_OFF=y
+CONFIG_ARCH_CPU_INIT=y
+CONFIG_SYS_THUMB_BUILD=y
+CONFIG_ARCH_KIRKWOOD=y
+CONFIG_SYS_KWD_CONFIG="board/cloudengines/pogo_v4/kwbimage.cfg"
+CONFIG_SYS_TEXT_BASE=0x600000
+CONFIG_TARGET_POGO_V4=y
+CONFIG_ENV_SIZE=0x20000
+CONFIG_ENV_OFFSET=0xC0000
+CONFIG_DEFAULT_DEVICE_TREE="kirkwood-pogoplug-series-4"
+CONFIG_IDENT_STRING="\nPogoplug V4"
+CONFIG_SYS_LOAD_ADDR=0x800000
+CONFIG_BOOTSTAGE=y
+CONFIG_SHOW_BOOT_PROGRESS=y
+CONFIG_BOOTDELAY=10
+CONFIG_USE_BOOTCOMMAND=y
+CONFIG_BOOTCOMMAND="setenv bootargs ${bootargs_console}; run bootcmd_usb; bootm 0x00800000 0x01100000 0x2c00000"
+CONFIG_USE_PREBOOT=y
+CONFIG_BOARD_LATE_INIT=y
+CONFIG_HUSH_PARSER=y
+CONFIG_SYS_PROMPT="Pogo_V4> "
+CONFIG_CMD_BOOTZ=y
+# CONFIG_BOOTM_PLAN9 is not set
+# CONFIG_BOOTM_RTEMS is not set
+# CONFIG_BOOTM_VXWORKS is not set
+# CONFIG_CMD_FLASH is not set
+CONFIG_CMD_MMC=y
+CONFIG_CMD_MTD=y
+CONFIG_CMD_NAND=y
+CONFIG_CMD_PCI=y
+CONFIG_CMD_SATA=y
+CONFIG_CMD_USB=y
+CONFIG_CMD_DHCP=y
+CONFIG_CMD_MII=y
+CONFIG_CMD_PING=y
+CONFIG_CMD_SNTP=y
+CONFIG_CMD_DNS=y
+CONFIG_CMD_EXT2=y
+CONFIG_CMD_EXT4=y
+CONFIG_CMD_FAT=y
+CONFIG_CMD_FS_GENERIC=y
+CONFIG_CMD_JFFS2=y
+CONFIG_CMD_MTDPARTS=y
+CONFIG_MTDIDS_DEFAULT="nand0=orion_nand"
+CONFIG_MTDPARTS_DEFAULT="mtdparts=orion_nand:2M(u-boot),3M(uImage),3M(uImage2),8M(failsafe),112M(root)"
+CONFIG_CMD_UBI=y
+CONFIG_ISO_PARTITION=y
+CONFIG_EFI_PARTITION=y
+CONFIG_PARTITION_TYPE_GUID=y
+CONFIG_OF_CONTROL=y
+CONFIG_ENV_OVERWRITE=y
+CONFIG_ENV_IS_IN_NAND=y
+CONFIG_VERSION_VARIABLE=y
+CONFIG_NET_RANDOM_ETHADDR=y
+CONFIG_NETCONSOLE=y
+CONFIG_DM=y
+CONFIG_SATA_MV=y
+CONFIG_KIRKWOOD_GPIO=y
+# CONFIG_MMC_HW_PARTITIONING is not set
+CONFIG_MVEBU_MMC=y
+CONFIG_MTD=y
+CONFIG_MTD_RAW_NAND=y
+CONFIG_PHY_MARVELL=y
+CONFIG_DM_ETH=y
+CONFIG_MVGBE=y
+CONFIG_MII=y
+CONFIG_PCI=y
+CONFIG_PCI_MVEBU=y
+CONFIG_DM_RTC=y
+CONFIG_RTC_EMULATION=y
+CONFIG_SYS_NS16550=y
+CONFIG_USB=y
+CONFIG_USB_XHCI_HCD=y
+CONFIG_USB_XHCI_PCI=y
+CONFIG_USB_EHCI_HCD=y
+CONFIG_USB_STORAGE=y
+CONFIG_JFFS2_LZO=y
+CONFIG_JFFS2_NAND=y
diff --git a/include/configs/goflexhome.h b/include/configs/goflexhome.h
index 90e37d9..c279579 100644
--- a/include/configs/goflexhome.h
+++ b/include/configs/goflexhome.h
@@ -1,5 +1,6 @@
 /* SPDX-License-Identifier: GPL-2.0+ */
 /*
+ * Copyright (C) 2022 Tony Dinh <mibodhi@gmai.com>
  * Copyright (C) 2013 Suriyan Ramasami <suriyan.r@gmail.com>
  *
  * Based on dockstar.h originally written by
@@ -14,55 +15,40 @@
 #ifndef _CONFIG_GOFLEXHOME_H
 #define _CONFIG_GOFLEXHOME_H
 
+#include <linux/bitops.h>
+
 /*
  * Default GPIO configuration and LED status
  */
 #define GOFLEXHOME_OE_LOW               (~(0))
 #define GOFLEXHOME_OE_HIGH              (~(0))
-#define GOFLEXHOME_OE_VAL_LOW           (1 << 29)       /* USB_PWEN low */
-#define GOFLEXHOME_OE_VAL_HIGH          (1 << 17)       /* LED pin high */
-
-/* PHY related */
-#define MV88E1116_LED_FCTRL_REG         10
-#define MV88E1116_CPRSP_CR3_REG         21
-#define MV88E1116_MAC_CTRL_REG          21
-#define MV88E1116_PGADR_REG             22
-#define MV88E1116_RGMII_TXTM_CTRL       (1 << 4)
-#define MV88E1116_RGMII_RXTM_CTRL       (1 << 5)
+#define GOFLEXHOME_OE_VAL_LOW		BIT(29)		/* USB_PWEN low */
+#define GOFLEXHOME_OE_VAL_HIGH          BIT(17)		/* LED pin high */
 
 #include "mv-common.h"
 
 /*
- *  Environment variables configurations
- */
-/*
- * max 4k env size is enough, but in case of nand
- * it has to be rounded to sector size
- */
-
-/*
  * Default environment variables
  */
 
 #define CONFIG_EXTRA_ENV_SETTINGS \
 	"console=console=ttyS0,115200\0" \
 	"mtdids=nand0=orion_nand\0" \
-	"mtdparts="CONFIG_MTDPARTS_DEFAULT \
+	"mtdparts=" CONFIG_MTDPARTS_DEFAULT \
 	"kernel=/boot/uImage\0" \
 	"bootargs_root=ubi.mtd=root root=ubi0:root rootfstype=ubifs ro\0"
 
 /*
  * Ethernet Driver configuration
  */
-#ifdef CONFIG_CMD_NET
 #define CONFIG_MVGBE_PORTS	{1, 0}	/* enable port 0 only */
 #define CONFIG_PHY_BASE_ADR	0
-#endif /* CONFIG_CMD_NET */
+#ifdef CONFIG_RESET_PHY_R
+#undef CONFIG_RESET_PHY_R      /* remove legacy reset_phy() */
+#endif
 
 /* SATA driver configuration */
-#ifdef CONFIG_SATA
 #define CONFIG_SYS_SATA_MAX_DEVICE	1
 #define CONFIG_LBA48
-#endif /* CONFIG_SATA */
 
 #endif /* _CONFIG_GOFLEXHOME_H */
diff --git a/include/configs/pogo_v4.h b/include/configs/pogo_v4.h
new file mode 100644
index 0000000..568a936
--- /dev/null
+++ b/include/configs/pogo_v4.h
@@ -0,0 +1,56 @@
+/* SPDX-License-Identifier: GPL-2.0+ */
+/*
+ * Copyright (C) 2014-2022 Tony Dinh <mibodhi@gmail.com>
+ *
+ * Based on
+ * Copyright (C) 2012
+ * David Purdy <david.c.purdy@gmail.com>
+ *
+ * Based on Kirkwood support:
+ * (C) Copyright 2009
+ * Marvell Semiconductor <www.marvell.com>
+ * Written-by: Prafulla Wadaskar <prafulla@marvell.com>
+ */
+
+#ifndef _CONFIG_POGO_V4_H
+#define _CONFIG_POGO_V4_H
+
+/*
+ * mv-common.h should be defined after CMD configs since it used them
+ * to enable certain macros
+ */
+#include "mv-common.h"
+
+/*
+ * Default environment variables
+ */
+#define CONFIG_EXTRA_ENV_SETTINGS \
+	"dtb_file=/boot/dts/" CONFIG_DEFAULT_DEVICE_TREE ".dtb\0" \
+	"mtdparts=" CONFIG_MTDPARTS_DEFAULT "\0"\
+	"mtdids=nand0=orion_nand\0"\
+	"bootargs_console=console=ttyS0,115200\0" \
+	"bootcmd_usb=usb start; load usb 0:1 0x00800000 /boot/uImage; " \
+	"load usb 0:1 0x01100000 /boot/uInitrd; " \
+	"load usb 0:1 0x2c00000 $dtb_file\0"
+
+/*
+ * Ethernet Driver configuration
+ */
+#define CONFIG_MVGBE_PORTS	{1, 0}	/* enable port 0 only */
+#define CONFIG_PHY_BASE_ADR	0
+#ifdef CONFIG_RESET_PHY_R
+#undef CONFIG_RESET_PHY_R	/* remove legacy reset_phy() */
+#endif
+
+/*
+ *  SATA Driver configuration
+ */
+#define CONFIG_SYS_SATA_MAX_DEVICE	1
+
+/*
+ * Support large disk for SATA and USB
+ */
+#define CONFIG_SYS_64BIT_LBA
+#define CONFIG_LBA48
+
+#endif /* _CONFIG_POGO_V4_H */
diff --git a/tools/kwboot.c b/tools/kwboot.c
index c3d8ab6..2684f0e 100644
--- a/tools/kwboot.c
+++ b/tools/kwboot.c
@@ -63,7 +63,6 @@
 #define EOT	4	/* sender end of block transfer */
 #define ACK	6	/* target block ack */
 #define NAK	21	/* target block negative ack */
-#define CAN	24	/* target/sender transfer cancellation */
 
 #define KWBOOT_XM_BLKSZ	128 /* xmodem block size */
 
@@ -75,7 +74,7 @@
 	uint8_t csum;
 } __packed;
 
-#define KWBOOT_BLK_RSP_TIMEO 1000 /* ms */
+#define KWBOOT_BLK_RSP_TIMEO 2000 /* ms */
 #define KWBOOT_HDR_RSP_TIMEO 10000 /* ms */
 
 /* ARM code to change baudrate */
@@ -293,13 +292,15 @@
 static ssize_t
 kwboot_write(int fd, const char *buf, size_t len)
 {
-	size_t tot = 0;
+	ssize_t tot = 0;
 
 	while (tot < len) {
 		ssize_t wr = write(fd, buf + tot, len - tot);
 
-		if (wr < 0)
-			return -1;
+		if (wr < 0 && errno == EINTR)
+			continue;
+		else if (wr < 0)
+			return wr;
 
 		tot += wr;
 	}
@@ -408,15 +409,19 @@
 
 	do {
 		nfds = select(fd + 1, &rfds, NULL, NULL, &tv);
-		if (nfds < 0)
+		if (nfds < 0 && errno == EINTR)
+			continue;
+		else if (nfds < 0)
 			goto out;
-		if (!nfds) {
+		else if (!nfds) {
 			errno = ETIMEDOUT;
 			goto out;
 		}
 
 		n = read(fd, buf, len);
-		if (n <= 0)
+		if (n < 0 && errno == EINTR)
+			continue;
+		else if (n <= 0)
 			goto out;
 
 		buf = (char *)buf + n;
@@ -718,6 +723,7 @@
 static int
 kwboot_bootmsg(int tty, void *msg)
 {
+	struct kwboot_block block;
 	int rc;
 	char c;
 	int count;
@@ -748,7 +754,40 @@
 
 	kwboot_printv("\n");
 
-	return rc;
+	if (rc)
+		return rc;
+
+	/*
+	 * At this stage we have sent more boot message patterns and BootROM
+	 * (at least on Armada XP and 385) started interpreting sent bytes as
+	 * part of xmodem packets. If BootROM is expecting SOH byte as start of
+	 * a xmodem packet and it receives byte 0xff, then it throws it away and
+	 * sends a NAK reply to host. If BootROM does not receive any byte for
+	 * 2s when expecting some continuation of the xmodem packet, it throws
+	 * away the partially received xmodem data and sends NAK reply to host.
+	 *
+	 * Therefore for starting xmodem transfer we have two options: Either
+	 * wait 2s or send 132 0xff bytes (which is the size of xmodem packet)
+	 * to ensure that BootROM throws away any partially received data.
+	 */
+
+	/* flush output queue with remaining boot message patterns */
+	tcflush(tty, TCOFLUSH);
+
+	/* send one xmodem packet with 0xff bytes to force BootROM to re-sync */
+	memset(&block, 0xff, sizeof(block));
+	kwboot_tty_send(tty, &block, sizeof(block), 0);
+
+	/*
+	 * Sending 132 bytes via 115200B/8-N-1 takes 11.45 ms, reading 132 bytes
+	 * takes 11.45 ms, so waiting for 30 ms should be enough.
+	 */
+	usleep(30 * 1000);
+
+	/* flush remaining NAK replies from input queue */
+	tcflush(tty, TCIFLUSH);
+
+	return 0;
 }
 
 static int
@@ -826,7 +865,7 @@
 static int
 _is_xm_reply(char c)
 {
-	return c == ACK || c == NAK || c == CAN;
+	return c == ACK || c == NAK;
 }
 
 static int
@@ -841,9 +880,6 @@
 	case NAK:
 		errno = EBADMSG;
 		break;
-	case CAN:
-		errno = ECANCELED;
-		break;
 	default:
 		errno = EPROTO;
 		break;
@@ -879,7 +915,8 @@
 }
 
 static int
-kwboot_xm_recv_reply(int fd, char *c, int nak_on_non_xm,
+kwboot_xm_recv_reply(int fd, char *c, int stop_on_non_xm,
+		     int ignore_nak_reply,
 		     int allow_non_xm, int *non_xm_print,
 		     int baudrate, int *baud_changed)
 {
@@ -899,8 +936,14 @@
 		}
 
 		/* If received xmodem reply, end. */
-		if (_is_xm_reply(*c))
+		if (_is_xm_reply(*c)) {
+			if (*c == NAK && ignore_nak_reply) {
+				timeout = recv_until - _now();
+				if (timeout >= 0)
+					continue;
+			}
 			break;
+		}
 
 		/*
 		 * If receiving/printing non-xmodem text output is allowed and
@@ -928,10 +971,8 @@
 				*non_xm_print = 1;
 			}
 		} else {
-			if (nak_on_non_xm) {
-				*c = NAK;
+			if (stop_on_non_xm)
 				break;
-			}
 			timeout = recv_until - _now();
 			if (timeout < 0) {
 				errno = ETIMEDOUT;
@@ -945,7 +986,7 @@
 
 static int
 kwboot_xm_sendblock(int fd, struct kwboot_block *block, int allow_non_xm,
-		    int *done_print, int baudrate)
+		    int *done_print, int baudrate, int allow_retries)
 {
 	int non_xm_print, baud_changed;
 	int rc, err, retries;
@@ -959,7 +1000,7 @@
 	do {
 		rc = kwboot_tty_send(fd, block, sizeof(*block), 1);
 		if (rc)
-			return rc;
+			goto err;
 
 		if (allow_non_xm && !*done_print) {
 			kwboot_progress(100, '.');
@@ -968,29 +1009,32 @@
 		}
 
 		rc = kwboot_xm_recv_reply(fd, &c, retries < 3,
+					  retries > 8,
 					  allow_non_xm, &non_xm_print,
 					  baudrate, &baud_changed);
 		if (rc)
-			goto can;
+			goto err;
 
-		if (!allow_non_xm && c != ACK)
-			kwboot_progress(-1, '+');
-	} while (c == NAK && retries++ < 16);
+		if (!allow_non_xm && c != ACK) {
+			if (c == NAK && allow_retries && retries + 1 < 16)
+				kwboot_progress(-1, '+');
+			else
+				kwboot_progress(-1, 'E');
+		}
+	} while (c == NAK && allow_retries && retries++ < 16);
 
 	if (non_xm_print)
 		kwboot_printv("\n");
 
 	if (allow_non_xm && baudrate && !baud_changed) {
 		fprintf(stderr, "Baudrate was not changed\n");
-		rc = -1;
 		errno = EPROTO;
-		goto can;
+		return -1;
 	}
 
 	return _xm_reply_to_error(c);
-can:
+err:
 	err = errno;
-	kwboot_tty_send_char(fd, CAN);
 	kwboot_printv("\n");
 	errno = err;
 	return rc;
@@ -1011,6 +1055,7 @@
 			return rc;
 
 		rc = kwboot_xm_recv_reply(fd, &c, retries < 3,
+					  retries > 8,
 					  0, NULL, 0, NULL);
 		if (rc)
 			return rc;
@@ -1043,8 +1088,30 @@
 
 		last_block = (left <= blksz);
 
+		/*
+		 * Handling of repeated xmodem packets is completely broken in
+		 * Armada 385 BootROM - it completely ignores xmodem packet
+		 * numbers, they are only used for checksum verification.
+		 * BootROM can handle a retry of the xmodem packet only during
+		 * the transmission of kwbimage header and only if BootROM
+		 * itself sent NAK response to previous attempt (it does it on
+		 * checksum failure). During the transmission of kwbimage data
+		 * part, BootROM always expects next xmodem packet, even if it
+		 * sent NAK to previous attempt - there is absolutely no way to
+		 * repair incorrectly transmitted xmodem packet during kwbimage
+		 * data part upload. Also, if kwboot receives non-ACK/NAK
+		 * response (meaning that original BootROM response was damaged
+		 * on UART) there is no way to detect if BootROM accepted xmodem
+		 * packet or not and no way to check if kwboot could repeat the
+		 * packet or not.
+		 *
+		 * Stop transfer and return failure if kwboot receives unknown
+		 * reply if non-xmodem reply is not allowed (for all xmodem
+		 * packets except the last header packet) or when non-ACK reply
+		 * is received during data part transfer.
+		 */
 		rc = kwboot_xm_sendblock(tty, &block, header && last_block,
-					 &done_print, baudrate);
+					 &done_print, baudrate, header);
 		if (rc)
 			goto out;
 
@@ -1081,10 +1148,6 @@
 	 */
 	hdrsz += (KWBOOT_XM_BLKSZ - hdrsz % KWBOOT_XM_BLKSZ) % KWBOOT_XM_BLKSZ;
 
-	kwboot_printv("Waiting 2s and flushing tty\n");
-	sleep(2); /* flush isn't effective without it */
-	tcflush(tty, TCIOFLUSH);
-
 	pnum = 1;
 
 	rc = kwboot_xmodem_one(tty, &pnum, 1, img, hdrsz, baudrate);
@@ -1568,6 +1631,7 @@
 			 * baudrate (which should be 115200) and do not touch
 			 * UART MPP configuration.
 			 */
+			hdr->flags |= 0x1;
 			hdr->options &= ~0x1F;
 			hdr->options |= MAIN_HDR_V1_OPT_BAUD_DEFAULT;
 			hdr->options |= 0 << 3;
@@ -1672,6 +1736,8 @@
 	size_t size;
 	size_t after_img_rsv;
 	int baudrate;
+	int prev_optind;
+	int c;
 
 	rv = 1;
 	tty = -1;
@@ -1689,22 +1755,32 @@
 	kwboot_verbose = isatty(STDOUT_FILENO);
 
 	do {
-		int c = getopt(argc, argv, "hb:ptaB:dD:q:s:o:");
+		prev_optind = optind;
+		c = getopt(argc, argv, "hbptaB:dD:q:s:o:");
 		if (c < 0)
 			break;
 
 		switch (c) {
 		case 'b':
+			if (imgpath || bootmsg || debugmsg)
+				goto usage;
 			bootmsg = kwboot_msg_boot;
-			imgpath = optarg;
+			if (prev_optind == optind)
+				goto usage;
+			if (argv[optind] && argv[optind][0] != '-')
+				imgpath = argv[optind++];
 			break;
 
 		case 'D':
+			if (imgpath || bootmsg || debugmsg)
+				goto usage;
 			bootmsg = NULL;
 			imgpath = optarg;
 			break;
 
 		case 'd':
+			if (imgpath || bootmsg || debugmsg)
+				goto usage;
 			debugmsg = kwboot_msg_debug;
 			break;
 
@@ -1744,14 +1820,14 @@
 		}
 	} while (1);
 
-	if (!bootmsg && !term && !debugmsg)
-		goto usage;
-
-	if (argc - optind < 1)
+	if (!bootmsg && !term && !debugmsg && !imgpath)
 		goto usage;
 
 	ttypath = argv[optind++];
 
+	if (optind != argc)
+		goto usage;
+
 	tty = kwboot_open_tty(ttypath, imgpath ? 115200 : baudrate);
 	if (tty < 0) {
 		perror(ttypath);