On 9/23/26 4:17 PM, Carlo Caione wrote:
> 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.

This is a bit short on details of why certain tecnical descisions are made
in this patch.

> 
> 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       | 17 ++++++
>  .../dts/mtk-genio-loader-spl-binman-u-boot.dtsi    |  2 +-
>  arch/arm/mach-mediatek/Kconfig                     | 28 +++++++++
>  arch/arm/mach-mediatek/Makefile                    |  3 +
>  arch/arm/mach-mediatek/spl_fastboot.c              | 68 
> ++++++++++++++++++++++
>  board/mediatek/MAINTAINERS                         |  5 ++
>  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 +
>  drivers/usb/mtu3/mtu3_core.c                       |  5 +-
>  15 files changed, 233 insertions(+), 3 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..9d0d057cfc9
> --- /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_MTK_BROM_DOWNLOAD_AGENT_SPL_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..9627785cc56
> --- /dev/null
> +++ b/arch/arm/dts/mtk-genio-da-binman-u-boot.dtsi
> @@ -0,0 +1,17 @@
> +// 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>;
> +
> +/* DA authentication is handled by the BootROM download tooling. */
> +#define MTK_GENIO_SPL_NO_FIT_KEYS
> +#include "mtk-genio-loader-spl-binman-u-boot.dtsi"
> +#undef MTK_GENIO_SPL_NO_FIT_KEYS
> +     };
> +};
> 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..6c99d0926c4 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,7 @@ ddr-loader {
>       size = <CONFIG_MTK_GENIO_DDR_LOADER_SIZE>;
>  };
>  
> -#ifdef CONFIG_SPL_FIT_SIGNATURE
> +#if defined(CONFIG_SPL_FIT_SIGNATURE) && !defined(MTK_GENIO_SPL_NO_FIT_KEYS)
>  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..eece6456e43 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 MTK_BROM_DOWNLOAD_AGENT_SPL_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..2a371664d1d 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_MTK_BROM_DOWNLOAD_AGENT_SPL_FASTBOOT)   += spl_fastboot.o
> +endif
>  
>  obj-$(CONFIG_TARGET_MT7622) += mt7622/
>  obj-$(CONFIG_TARGET_MT7623) += mt7623/
> diff --git a/arch/arm/mach-mediatek/spl_fastboot.c 
> b/arch/arm/mach-mediatek/spl_fastboot.c
> new file mode 100644
> index 00000000000..73744946314
> --- /dev/null
> +++ b/arch/arm/mach-mediatek/spl_fastboot.c
> @@ -0,0 +1,68 @@
> +// 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 <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);
> +
> +     if (!mmc->ext_csd[EXT_CSD_RST_N_FUNCTION]) {
> +             ret = mmc_set_rst_n_function(mmc, 1);

If I understand correctly, this makes a permanant change to the eMMC hardware.
It is documented in patch 3, but I wonder if we should add a comment here too.
And I wonder if anyone would not want that setting.

> +             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..61fefcf9a34 100644
> --- a/board/mediatek/MAINTAINERS
> +++ b/board/mediatek/MAINTAINERS
> @@ -18,13 +18,18 @@ MT8188/MT8370/MT8390
>  M:   Macpaul Lin <[email protected]>
>  M:   Julien Stephan <[email protected]>
>  S:   Maintained
> +F:   arch/arm/dts/mt8370-genio-da-u-boot.dtsi
>  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:   configs/mt8370-genio-da-spl-fastboot.config
> +F:   configs/mt8370-genio-da.config

These are not sorted in order.

>  F:   configs/mt8188.config
> +F:   configs/mt8370_genio_510_evk_da_spl_defconfig
>  F:   configs/mt8370_genio_510_evk_defconfig
> +F:   configs/mt8390_genio_700_evk_da_spl_defconfig
>  F:   configs/mt8390_genio_700_evk_defconfig
>  F:   doc/board/mediatek/mt8188-genio-evk.rst
>  
> diff --git a/common/spl/Kconfig b/common/spl/Kconfig
> index 9bce4ab3955..c6fa647670b 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..6ba12f7d282
> --- /dev/null
> +++ b/configs/mt8370-genio-da-spl-fastboot.config
> @@ -0,0 +1,21 @@
> +#include <configs/mt8370-genio-da.config>
> +
> +CONFIG_MTK_BROM_DOWNLOAD_AGENT_SPL_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>
> diff --git a/drivers/usb/mtu3/mtu3_core.c b/drivers/usb/mtu3/mtu3_core.c
> index f296a72cf18..d8ef6e6afba 100644
> --- a/drivers/usb/mtu3/mtu3_core.c
> +++ b/drivers/usb/mtu3/mtu3_core.c
> @@ -843,7 +843,10 @@ int ssusb_gadget_init(struct ssusb_mtk *ssusb)
>       mtu->mac_base = ssusb->mac_base;
>       mtu->ssusb = ssusb;
>       mtu->max_speed = usb_get_maximum_speed(dev_ofnode(ssusb->dev));
> -     mtu->force_vbus = dev_read_bool(ssusb->dev, "mediatek,force-vbus");
> +     /* Fixed peripheral mode must not depend on OTG session detection. */

Why not? From what I am seeing in the Linux driver it doesn't do this.
And I'm not sure why mt8183 has "mediatek,force-vbus" here in the U-boot
devicetree. Maybe lack of proper pinmux for that target in U-boot?

I feel like we should not be doing this for new boards. I would only expect
to need to force vbus on a board where vbus wasn't wired up properly. That
isn't the case here.

Is fastboot broken without this change?

> +     mtu->force_vbus =
> +             usb_get_dr_mode(dev_ofnode(ssusb->dev)) == 
> USB_DR_MODE_PERIPHERAL ||
> +             dev_read_bool(ssusb->dev, "mediatek,force-vbus");
>  
>       ret = mtu3_hw_init(mtu);
>       if (ret) {
> 

Reply via email to