From: Julien Masson <[email protected]>

Genio 510 and 700 need a way to provision blank eMMC and recover from
unusable boot firmware without relying on the installed bootloader. Add
a BootROM-loaded fastboot agent that also prepares the eMMC boot
settings so newly flashed firmware can boot.

U-Boot proper is preferred when the complete agent fits BootROM's SRAM
download area before DRAM initialization. Provide the SPL alternative
for tighter payload budgets, avoiding the space required by BL31 and
U-Boot proper. An external DDR loader is still required.

DA authentication belongs to the BootROM download flow, so provisioning
agents must not require the keys used to sign normal storage images.
Sparse flashing needs a 16 MiB heap to accommodate the writer's 8 MiB
buffer alongside fastboot state.

Signed-off-by: Julien Masson <[email protected]>
Signed-off-by: Carlo Caione <[email protected]>
---
 arch/arm/dts/mt8370-genio-510-evk-u-boot.dtsi      |  4 ++
 arch/arm/dts/mt8370-genio-da-u-boot.dtsi           | 61 +++++++++++++++++++
 arch/arm/dts/mt8390-genio-700-evk-u-boot.dtsi      |  4 ++
 arch/arm/dts/mtk-genio-da-binman-u-boot.dtsi       | 14 +++++
 .../dts/mtk-genio-loader-spl-binman-u-boot.dtsi    |  3 +-
 arch/arm/mach-mediatek/Kconfig                     | 28 +++++++++
 arch/arm/mach-mediatek/Makefile                    |  3 +
 arch/arm/mach-mediatek/download_agent.c            | 70 ++++++++++++++++++++++
 board/mediatek/MAINTAINERS                         | 12 ++--
 common/spl/Kconfig                                 |  2 +-
 configs/mt8370-genio-da-spl-fastboot.config        | 21 +++++++
 configs/mt8370-genio-da.config                     | 12 ++++
 configs/mt8370_genio_510_evk_da_spl_defconfig      |  2 +
 configs/mt8390_genio_700_evk_da_spl_defconfig      |  2 +
 14 files changed, 229 insertions(+), 9 deletions(-)

diff --git a/arch/arm/dts/mt8370-genio-510-evk-u-boot.dtsi 
b/arch/arm/dts/mt8370-genio-510-evk-u-boot.dtsi
index 10b9a142f37..2ee7fb1f40c 100644
--- a/arch/arm/dts/mt8370-genio-510-evk-u-boot.dtsi
+++ b/arch/arm/dts/mt8370-genio-510-evk-u-boot.dtsi
@@ -14,3 +14,7 @@
 #include "mtk-genio-mtk-boot-binman-u-boot.dtsi"
 #include "mtk-genio-bootloaders-binman-u-boot.dtsi"
 #endif
+
+#ifdef CONFIG_MTK_BROM_DOWNLOAD_AGENT
+#include "mt8370-genio-da-u-boot.dtsi"
+#endif
diff --git a/arch/arm/dts/mt8370-genio-da-u-boot.dtsi 
b/arch/arm/dts/mt8370-genio-da-u-boot.dtsi
new file mode 100644
index 00000000000..f37ec34b0f0
--- /dev/null
+++ b/arch/arm/dts/mt8370-genio-da-u-boot.dtsi
@@ -0,0 +1,61 @@
+// SPDX-License-Identifier: (GPL-2.0-only OR MIT)
+/*
+ * Copyright (c) 2026 BayLibre, SAS.
+ * Author: Carlo Caione <[email protected]>
+ */
+
+/*
+ * Download agents (DAs) run from RAM to provision or recover eMMC.
+ * Both variants expose USB0 as a peripheral and leave unused USB
+ * controllers disabled, independently of the normal boot USB setup.
+ */
+
+#include "mtk-genio-binman-u-boot.dtsi"
+#include "mtk-genio-da-binman-u-boot.dtsi"
+
+&ssusb0 {
+       dr_mode = "peripheral";
+};
+
+&ssusb1 {
+       status = "disabled";
+};
+
+&ssusb2 {
+       status = "disabled";
+};
+
+/* Only the SPL fastboot variant needs these USB dependencies in SPL. */
+#ifdef CONFIG_SPL_MTK_BROM_DOWNLOAD_AGENT_FASTBOOT
+&pericfg_ao {
+       bootph-pre-ram;
+};
+
+&ssusb0 {
+       bootph-pre-ram;
+};
+
+&u3phy0 {
+       bootph-pre-ram;
+};
+
+&u2port0 {
+       bootph-pre-ram;
+};
+
+&usb_default_pins {
+       bootph-pre-ram;
+
+       pins-iddig {
+               bootph-pre-ram;
+       };
+
+       pins-valid {
+               bootph-pre-ram;
+       };
+
+       pins-vbus {
+               bootph-pre-ram;
+       };
+};
+#endif
diff --git a/arch/arm/dts/mt8390-genio-700-evk-u-boot.dtsi 
b/arch/arm/dts/mt8390-genio-700-evk-u-boot.dtsi
index 6230b016ca0..4fedbda9b3f 100644
--- a/arch/arm/dts/mt8390-genio-700-evk-u-boot.dtsi
+++ b/arch/arm/dts/mt8390-genio-700-evk-u-boot.dtsi
@@ -14,3 +14,7 @@
 #include "mtk-genio-mtk-boot-binman-u-boot.dtsi"
 #include "mtk-genio-bootloaders-binman-u-boot.dtsi"
 #endif
+
+#ifdef CONFIG_MTK_BROM_DOWNLOAD_AGENT
+#include "mt8370-genio-da-u-boot.dtsi"
+#endif
diff --git a/arch/arm/dts/mtk-genio-da-binman-u-boot.dtsi 
b/arch/arm/dts/mtk-genio-da-binman-u-boot.dtsi
new file mode 100644
index 00000000000..eb956c91a80
--- /dev/null
+++ b/arch/arm/dts/mtk-genio-da-binman-u-boot.dtsi
@@ -0,0 +1,14 @@
+// SPDX-License-Identifier: (GPL-2.0-only OR MIT)
+/*
+ * Copyright (c) 2026 BayLibre, SAS.
+ * Author: Carlo Caione <[email protected]>
+ */
+
+&binman {
+       da: da {
+               filename = "da.bin";
+               pad-byte = <0>;
+
+#include "mtk-genio-loader-spl-binman-u-boot.dtsi"
+       };
+};
diff --git a/arch/arm/dts/mtk-genio-loader-spl-binman-u-boot.dtsi 
b/arch/arm/dts/mtk-genio-loader-spl-binman-u-boot.dtsi
index 2dd13d261a0..8c676a6e05e 100644
--- a/arch/arm/dts/mtk-genio-loader-spl-binman-u-boot.dtsi
+++ b/arch/arm/dts/mtk-genio-loader-spl-binman-u-boot.dtsi
@@ -12,7 +12,8 @@ ddr-loader {
        size = <CONFIG_MTK_GENIO_DDR_LOADER_SIZE>;
 };
 
-#ifdef CONFIG_SPL_FIT_SIGNATURE
+/* DA authentication is handled by the BootROM download tooling. */
+#if defined(CONFIG_SPL_FIT_SIGNATURE) && 
!defined(CONFIG_MTK_BROM_DOWNLOAD_AGENT)
 u-boot-spl {
        type = "section";
        size = <CONFIG_SPL_MAX_SIZE>;
diff --git a/arch/arm/mach-mediatek/Kconfig b/arch/arm/mach-mediatek/Kconfig
index e572cfe8571..8b2534a19fc 100644
--- a/arch/arm/mach-mediatek/Kconfig
+++ b/arch/arm/mach-mediatek/Kconfig
@@ -249,6 +249,34 @@ config MTK_GENIO_BL31_LOAD_ADDR
 
 endif
 
+config MTK_BROM_DOWNLOAD_AGENT
+       bool
+       depends on TARGET_MT8188 && SPL
+       select BINMAN
+       select MTK_GENIO_IMAGE_CONTRACT
+
+choice
+       prompt "MediaTek BootROM download agent"
+       optional
+       depends on TARGET_MT8188 && SPL && SUPPORT_EMMC_BOOT
+       depends on !MTK_GENIO_BOOT_IMAGES
+       help
+         Select where to run fastboot after the BootROM downloads the agent
+         into RAM. Leave this disabled for normal storage boot.
+         Download agents cannot also build the normal storage-boot images.
+
+config SPL_MTK_BROM_DOWNLOAD_AGENT_FASTBOOT
+       bool "Run download-agent fastboot from SPL"
+       depends on SPL_FASTBOOT_FLASH_MMC
+       select MTK_BROM_DOWNLOAD_AGENT
+       select SPL_BOARD_INIT
+       help
+         Build an SPL which enters USB fastboot after the MediaTek BootROM
+         downloads it into RAM. The download agent also configures the eMMC
+         boot partition so that a newly flashed board can boot normally.
+
+endchoice
+
 config MTK_TZ_MOVABLE
        select ARCH_MISC_INIT
        select OF_SYSTEM_SETUP
diff --git a/arch/arm/mach-mediatek/Makefile b/arch/arm/mach-mediatek/Makefile
index 35f748a70d6..e052fbda73e 100644
--- a/arch/arm/mach-mediatek/Makefile
+++ b/arch/arm/mach-mediatek/Makefile
@@ -4,6 +4,9 @@ obj-$(CONFIG_ARM64) += armv8-mem-map.o
 obj-y  += cpu.o
 obj-$(CONFIG_MTK_TZ_MOVABLE)   += tzcfg.o
 obj-$(CONFIG_XPL_BUILD)        += spl.o
+ifdef CONFIG_XPL_BUILD
+obj-$(CONFIG_SPL_MTK_BROM_DOWNLOAD_AGENT_FASTBOOT)     += download_agent.o
+endif
 
 obj-$(CONFIG_TARGET_MT7622) += mt7622/
 obj-$(CONFIG_TARGET_MT7623) += mt7623/
diff --git a/arch/arm/mach-mediatek/download_agent.c 
b/arch/arm/mach-mediatek/download_agent.c
new file mode 100644
index 00000000000..da17fb4b309
--- /dev/null
+++ b/arch/arm/mach-mediatek/download_agent.c
@@ -0,0 +1,70 @@
+// SPDX-License-Identifier: GPL-2.0-only
+/*
+ * Copyright (c) 2026 BayLibre, SAS.
+ * Author: Julien Masson <[email protected]>
+ */
+
+#include <dm/uclass.h>
+#include <fastboot.h>
+#include <mmc.h>
+#include <spl.h>
+#include <stdio.h>
+#include <linux/errno.h>
+
+static int mtk_mmc_boot_prepare(void)
+{
+       struct udevice *dev;
+       struct mmc *mmc;
+       int ret;
+
+       /* No storage loader has run yet, so probe the device here. */
+       ret = uclass_get_device_by_seq(UCLASS_MMC,
+                                      CONFIG_VAL(FASTBOOT_FLASH_MMC_DEV), 
&dev);
+       if (ret) {
+               printf("Cannot load MMC device: %d\n", ret);
+               return ret;
+       }
+
+       mmc = mmc_get_mmc_dev(dev);
+       if (!mmc)
+               return -ENODEV;
+
+       ret = mmc_init(mmc);
+       if (ret) {
+               printf("MMC init failed: %d\n", ret);
+               return ret;
+       }
+
+       /* Enable BOOT1 and boot acknowledgment for normal BootROM startup. */
+       ret = mmc_set_part_conf(mmc, 1, 1, 0);
+       if (ret)
+               printf("Cannot configure the eMMC boot partition: %d\n", ret);
+
+       /* Reset to x1 SDR, backward-compatible timing for each boot. */
+       ret = mmc_set_boot_bus_width(mmc, 0, 0, 0);
+       if (ret)
+               printf("Cannot configure the eMMC boot bus: %d\n", ret);
+
+       /* This permanently enables the reset pin; it cannot be undone. */
+       if (!mmc->ext_csd[EXT_CSD_RST_N_FUNCTION]) {
+               ret = mmc_set_rst_n_function(mmc, 1);
+               if (ret)
+                       printf("Cannot enable the eMMC reset function: %d\n", 
ret);
+       }
+
+       return 0;
+}
+
+void spl_board_init(void)
+{
+       int ret;
+
+       ret = mtk_mmc_boot_prepare();
+       if (ret)
+               printf("MMC boot preparation failed: %d\n", ret);
+
+       puts("Waiting for fastboot commands...\n");
+       ret = fastboot_usb_run(0, NULL, 0);
+       if (ret)
+               printf("Fastboot failed: %d\n", ret);
+}
diff --git a/board/mediatek/MAINTAINERS b/board/mediatek/MAINTAINERS
index 20befdba0e2..696b87c1524 100644
--- a/board/mediatek/MAINTAINERS
+++ b/board/mediatek/MAINTAINERS
@@ -18,14 +18,12 @@ MT8188/MT8370/MT8390
 M:     Macpaul Lin <[email protected]>
 M:     Julien Stephan <[email protected]>
 S:     Maintained
-F:     arch/arm/dts/mt8370-genio-510-evk-u-boot.dtsi
-F:     arch/arm/dts/mt8390-genio-700-evk-u-boot.dtsi
-F:     arch/arm/dts/mt8390-genio-common-u-boot.dtsi
-F:     arch/arm/dts/mtk-genio-*-binman-u-boot.dtsi
-F:     arch/arm/dts/mtk-genio-binman-u-boot.dtsi
+F:     arch/arm/dts/mt8370*
+F:     arch/arm/dts/mt8390*
+F:     arch/arm/dts/mtk-genio*
 F:     configs/mt8188.config
-F:     configs/mt8370_genio_510_evk_defconfig
-F:     configs/mt8390_genio_700_evk_defconfig
+F:     configs/mt8370*
+F:     configs/mt8390*
 F:     doc/board/mediatek/mt8188-genio-evk.rst
 
 MT8195/MT8395
diff --git a/common/spl/Kconfig b/common/spl/Kconfig
index 4930ecb0861..fb8bbbd2f5c 100644
--- a/common/spl/Kconfig
+++ b/common/spl/Kconfig
@@ -194,7 +194,7 @@ config SPL_SHOW_ERRORS
 config SPL_BINMAN_SYMBOLS
        bool "Declare binman symbols in SPL"
        depends on SPL_FRAMEWORK && BINMAN
-       default n if MTK_GENIO_BOOT_IMAGES
+       default n if MTK_GENIO_IMAGE_CONTRACT
        default y
        help
          This enables use of symbols in SPL which refer to other entries in
diff --git a/configs/mt8370-genio-da-spl-fastboot.config 
b/configs/mt8370-genio-da-spl-fastboot.config
new file mode 100644
index 00000000000..a1c7d8d3d8e
--- /dev/null
+++ b/configs/mt8370-genio-da-spl-fastboot.config
@@ -0,0 +1,21 @@
+#include <configs/mt8370-genio-da.config>
+
+CONFIG_SPL_MTK_BROM_DOWNLOAD_AGENT_FASTBOOT=y
+# Sparse writes need an 8 MiB DMA buffer in addition to the fastboot state.
+CONFIG_SPL_SYS_MALLOC_SIZE=0x1000000
+# dlmalloc also caps individual SPL allocations at SYS_MALLOC_LEN.
+CONFIG_SYS_MALLOC_LEN=0x1000000
+# Resume from the user-area FIT after fastboot continue.
+CONFIG_SUPPORT_EMMC_BOOT_OVERRIDE_PART_CONFIG=y
+CONFIG_SYS_MMCSD_RAW_MODE_EMMC_BOOT_PARTITION=0
+CONFIG_SPL_MMC_WRITE=y
+CONFIG_SPL_PHY=y
+CONFIG_SPL_DM_USB_GADGET=y
+CONFIG_SPL_USB_GADGET=y
+CONFIG_SPL_USB_MTU3=y
+CONFIG_SPL_FASTBOOT=y
+CONFIG_SPL_FASTBOOT_REBOOT=y
+CONFIG_SPL_FASTBOOT_FLASH_MMC=y
+CONFIG_SPL_FASTBOOT_FLASH_MMC_DEV=0
+CONFIG_SPL_FASTBOOT_MMC_BOOT_SUPPORT=y
+CONFIG_SPL_FASTBOOT_MMC_USER_SUPPORT=y
diff --git a/configs/mt8370-genio-da.config b/configs/mt8370-genio-da.config
new file mode 100644
index 00000000000..46cb42b37ba
--- /dev/null
+++ b/configs/mt8370-genio-da.config
@@ -0,0 +1,12 @@
+# USB identity and transfer buffer shared by both download-agent modes.
+CONFIG_SUPPORT_EMMC_BOOT=y
+CONFIG_PHY=y
+CONFIG_PHY_MTK_TPHY=y
+CONFIG_USB=y
+CONFIG_DM_USB_GADGET=y
+CONFIG_USB_MTU3=y
+CONFIG_USB_GADGET=y
+CONFIG_USB_GADGET_VENDOR_NUM=0x0e8d
+CONFIG_USB_GADGET_PRODUCT_NUM=0x201c
+CONFIG_FASTBOOT_BUF_ADDR=0x65000000
+CONFIG_FASTBOOT_BUF_SIZE=0x15000000
diff --git a/configs/mt8370_genio_510_evk_da_spl_defconfig 
b/configs/mt8370_genio_510_evk_da_spl_defconfig
new file mode 100644
index 00000000000..bb537616b53
--- /dev/null
+++ b/configs/mt8370_genio_510_evk_da_spl_defconfig
@@ -0,0 +1,2 @@
+#include <configs/mt8370_genio_510_evk_defconfig>
+#include <configs/mt8370-genio-da-spl-fastboot.config>
diff --git a/configs/mt8390_genio_700_evk_da_spl_defconfig 
b/configs/mt8390_genio_700_evk_da_spl_defconfig
new file mode 100644
index 00000000000..7f1ba02c6e7
--- /dev/null
+++ b/configs/mt8390_genio_700_evk_da_spl_defconfig
@@ -0,0 +1,2 @@
+#include <configs/mt8390_genio_700_evk_defconfig>
+#include <configs/mt8370-genio-da-spl-fastboot.config>

-- 
2.56.0

Reply via email to