diff --git a/.github/workflows/build-boot.yml b/.github/workflows/build-boot.yml
index ca285be62..945ecd86b 100644
--- a/.github/workflows/build-boot.yml
+++ b/.github/workflows/build-boot.yml
@@ -19,6 +19,8 @@ jobs:
- aarch64_qemu_boot
- bpi_r3_sd_boot
- bpi_r3_emmc_boot
+ - bpi_r64_sd_boot
+ - bpi_r64_emmc_boot
- cn9130_crb_boot
- fireant_boot
- nanopi_r2s_boot
diff --git a/.github/workflows/build-image.yml b/.github/workflows/build-image.yml
index 27c9a9b86..497ef794f 100644
--- a/.github/workflows/build-image.yml
+++ b/.github/workflows/build-image.yml
@@ -11,6 +11,7 @@ on:
- raspberrypi-rpi2
- raspberrypi-rpi64
- bananapi-bpi-r3
+ - bananapi-bpi-r64
- friendlyarm-nanopi-r2s
- microchip-sama7g54-ek
default: 'raspberrypi-rpi64'
@@ -67,6 +68,12 @@ jobs:
echo "ARCH=aarch64" >> $GITHUB_ENV
echo "BUILD_EMMC=true" >> $GITHUB_ENV
;;
+ bananapi-bpi-r64)
+ echo "BOOTLOADER_SD=bpi-r64-sd-boot" >> $GITHUB_ENV
+ echo "BOOTLOADER_EMMC=bpi-r64-emmc-boot" >> $GITHUB_ENV
+ echo "ARCH=aarch64" >> $GITHUB_ENV
+ echo "BUILD_EMMC=true" >> $GITHUB_ENV
+ ;;
friendlyarm-nanopi-r2s)
echo "BOOTLOADER=nanopi-r2s-boot" >> $GITHUB_ENV
echo "ARCH=aarch64" >> $GITHUB_ENV
diff --git a/board/aarch64/Config.in b/board/aarch64/Config.in
index eac6607e6..a27864e8c 100644
--- a/board/aarch64/Config.in
+++ b/board/aarch64/Config.in
@@ -2,6 +2,7 @@ if BR2_aarch64
source "$BR2_EXTERNAL_INFIX_PATH/board/aarch64/alder-alder/Config.in"
source "$BR2_EXTERNAL_INFIX_PATH/board/aarch64/bananapi-bpi-r3/Config.in"
+source "$BR2_EXTERNAL_INFIX_PATH/board/aarch64/bananapi-bpi-r64/Config.in"
source "$BR2_EXTERNAL_INFIX_PATH/board/aarch64/freescale-imx8mp-evk/Config.in"
source "$BR2_EXTERNAL_INFIX_PATH/board/aarch64/friendlyarm-nanopi-r2s/Config.in"
source "$BR2_EXTERNAL_INFIX_PATH/board/aarch64/marvell-cn9130-crb/Config.in"
diff --git a/board/aarch64/README.md b/board/aarch64/README.md
index 9f2e217a3..074cfab48 100644
--- a/board/aarch64/README.md
+++ b/board/aarch64/README.md
@@ -4,7 +4,8 @@ aarch64
Board Specific Documentation
----------------------------
-- [Banana Pi R3](banana-pi-r3/)
+- [Banana Pi BPi-R3](banana-pi-r3/)
+- [Banana Pi BPi-R64](banana-pi-r64/)
- [Marvell CN9130-CRB](cn9130-crb/)
- [Microchip SparX-5i PCB135 (eMMC)](sparx5-pcb135/)
- [NanoPi R2S](r2s/)
diff --git a/board/aarch64/bananapi-bpi-r64/Config.in b/board/aarch64/bananapi-bpi-r64/Config.in
new file mode 100644
index 000000000..6b184d7c8
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/Config.in
@@ -0,0 +1,7 @@
+config BR2_PACKAGE_BANANAPI_BPI_R64
+ bool "Banana Pi R64"
+ depends on BR2_aarch64
+ select BR2_PACKAGE_FEATURE_WIFI
+ select SDCARD_AUX
+ help
+ Build Banana PI R64 support
diff --git a/board/aarch64/bananapi-bpi-r64/LICENSE b/board/aarch64/bananapi-bpi-r64/LICENSE
new file mode 100644
index 000000000..8cdb30a3a
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/LICENSE
@@ -0,0 +1,13 @@
+Copyright (c) 2026 The KernelKit Authors
+
+Permission to use, copy, modify, and/or distribute this software for any
+purpose with or without fee is hereby granted, provided that the above
+copyright notice and this permission notice appear in all copies.
+
+THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
diff --git a/board/aarch64/bananapi-bpi-r64/README.md b/board/aarch64/bananapi-bpi-r64/README.md
new file mode 100644
index 000000000..b9276b2f8
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/README.md
@@ -0,0 +1,188 @@
+# Banana Pi BPI-R64
+
+## Overview
+
+
+
+The Banana Pi BPI-R64 is a networking board based on the MediaTek MT7622
+(dual Cortex-A53, AArch64) SoC.
+
+### Hardware Features
+
+- MediaTek MT7622 ARM Cortex-A53 dual-core processor @ 1.35 GHz
+- 1 GB DDR3L RAM
+- 8 GB eMMC storage
+- microSD card slot
+- MT7531 Gigabit Ethernet switch (4x LAN + 1x WAN)
+- MT7603E built-in 2.4 GHz WiFi
+- USB 3.0 port
+- 2x Mini PCIe slots
+
+### Default Network Configuration
+
+Infix comes preconfigured with:
+
+- **LAN ports** (lan0-lan3): Bridged for internal networking
+- **WAN port**: DHCP client enabled for internet connectivity
+- **WiFi** (wifi0-ap): Bridged to LAN (MT7615 PCIe card if fitted, otherwise MT7603E)
+
+## Boot Switch Reference
+
+
+
+The BPI-R64 uses a 2-position DIP switch (SW1) to select the boot device
+order. The MT7622 Boot ROM tries devices in the order listed and falls
+back to the next if no valid BL2 is found at the expected location.
+
+| SW1 | Boot device | Use case |
+|-----|-------------|----------------------------|
+| OFF | eMMC | Production eMMC boot |
+| ON | SD card | SD card boot / development |
+
+> [!NOTE]
+> SinoVoip has exposed only one bit of the MT7622's two-bit `BOOT_SEL[1:0]`
+> strapping field via SW1, with `BOOT_SEL[1]` hardwired high. This limits the
+> board to eMMC (`10b`) and SD (`11b`) boot; the SPI-NOR and SPI-NAND modes
+> available on the MT7622 reference board (`00b`, `01b`) are not selectable.
+
+## Getting Started
+
+### Quick Start with SD Card
+
+1. **Flash the image to an SD card** (the filename includes the version, e.g.
+ `infix-25.01-bpi-r64-sdcard.img`):
+
+
+
+ ```sh
+ dd if=infix-*-bpi-r64-sdcard.img of=/dev/sdX bs=4M status=progress
+ ```
+
+2. **Set boot switch:** SW1 ON (SD card boot)
+3. **Insert SD card and power on**
+4. **Connect console:** 115200 8N1 — use the dedicated Debug UART header
+ just below the 40-pin GPIO header; pins are labeled GND, RX, TX on the board
+5. **Default login:** `admin` / `admin`
+
+## Installing to eMMC
+
+### eMMC Boot ROM Behaviour
+
+> [!IMPORTANT]
+> The MT7622 Boot ROM reads BL2 from two possible locations depending on the
+> eMMC configuration:
+>
+> - **eMMC BOOT0 hardware partition enabled** (factory default on most chips):
+> Boot ROM reads BL2 from offset 0 of the BOOT0 partition. Our disk image
+> (which puts BL2 in the User Data Area at sector 1024 / offset 0x80000) will
+> **not** be found here — you must either write BL2 to BOOT0 separately or
+> disable BOOT0.
+>
+> - **eMMC BOOT0 disabled:** Boot ROM falls through to the User Data Area (UDA)
+> and reads BL2 from sector 1024 (offset 0x80000). The eMMC BL2 is built
+> for BOOT0 (`hdroffset=0x0`) and will **not** match this location — BOOT0
+> must be enabled for eMMC boot to work.
+>
+> The recommended installation procedure below writes BL2 to BOOT0 and enables
+> BOOT0 as the boot source.
+
+### Procedure
+
+The easiest path is to boot from SD first and then write the eMMC image from
+U-Boot.
+
+#### Step 1: Boot from SD card
+
+1. Set SW1 to ON (SD boot)
+2. Insert SD card with Infix
+3. Power on and break into U-Boot (press Ctrl-C during boot)
+
+#### Step 2: Write the eMMC image from U-Boot
+
+Place `infix-bpi-r64-emmc.img` and `bl2.img` on a FAT32-formatted USB drive,
+then from the U-Boot prompt:
+
+```
+usb start
+fatload usb 0:1 0x44000000 infix-bpi-r64-emmc.img
+setexpr blocks ${filesize} / 0x200
+mmc dev 0
+mmc write 0x44000000 0x0 ${blocks}
+```
+
+#### Step 3: Write BL2 to eMMC BOOT0
+
+This handles the BOOT0 case and ensures the Boot ROM can find BL2 regardless
+of the chip's default BOOT0 state:
+
+```
+fatload usb 0:1 0x44000000 bl2.img
+mmc partconf 0 1 1 1
+setexpr blkcnt ${filesize} + 0x1ff
+setexpr blkcnt ${blkcnt} / 0x200
+mmc write 0x44000000 0x0 ${blkcnt}
+mmc partconf 0 1 1 0
+```
+
+The `mmc partconf 0 1 1 1` command enables BOOT0 and routes boot reads there;
+`mmc partconf 0 1 1 0` switches back to UDA access so U-Boot sees the full
+partition table normally.
+
+#### Step 4: Boot from eMMC
+
+1. Power off the board
+2. Set SW1 to OFF (eMMC boot)
+3. Remove SD card
+4. Remove USB drive
+5. Power on
+
+## Platform Notes
+
+### BL2 Offset and GPT Requirement (sector 1024)
+
+The MT7622 Boot ROM locates BL2 via the **GPT partition table**: it reads the
+GPT, finds the partition named `bl2`, and loads from its start sector. The
+`bl2` partition must start at **sector 1024 = offset 0x80000** (same as the
+MT7986/BPI-R3).
+
+> [!IMPORTANT]
+> The MT7622 Boot ROM reads the **legacy MBR partition table** to locate BL2,
+> not the GPT. The disk image must use a **hybrid MBR/GPT** layout so that the
+> `bl2` partition is visible in both tables. A pure GPT image causes `F5: 4801
+> 0000` → `F5: 480A 0031` → halt. `genimage` is configured with
+> `partition-table-type = "hybrid"` to produce the required layout.
+
+The ATF SD build uses `DEVICE_HEADER_OFFSET=0x80000` so that `mkimage` encodes
+the correct media position (sector 1024 of UDA) in the BRLYT `gfh_offset`
+field. The eMMC build uses `DEVICE_HEADER_OFFSET=0x0` because BL2 lives at
+offset 0 of the BOOT0 partition. Getting this wrong causes a `F5: 4801 0000`
+failure (found but rejected) rather than `F5: 480A 0031` (not found).
+
+### FIP Location
+
+BL2 locates the FIP (containing BL31 + U-Boot) by name via the GPT partition
+table — it looks for a partition labelled `fip`. No hardcoded FIP offset is
+used, so FIP can be placed freely after BL2 in the partition table.
+
+### mmc0 = eMMC, mmc1 = SD
+
+On MT7622, MSDC0 (mmc0 in U-Boot and Linux) is the 8-bit eMMC controller and
+MSDC1 (mmc1) is the 4-bit SD card controller. This is the reverse of many
+other platforms. The SD U-Boot environment therefore sets `boot_targets =
+"mmc1"` while the eMMC environment uses the default `mmc0`.
+
+## Building
+
+```sh
+# Bootloader only (SD)
+make O=x-boot-bpir64-sd bpi_r64_sd_boot_defconfig && make O=x-boot-bpir64-sd
+
+# Bootloader only (eMMC)
+make O=x-boot-bpir64-emmc bpi_r64_emmc_boot_defconfig && make O=x-boot-bpir64-emmc
+
+# Compose SD image (pass the Infix rootfs output directory)
+utils/mkimage.sh -b x-boot-bpir64-sd -r x-aarch64/images bananapi-bpi-r64
+
+# Compose eMMC image
+utils/mkimage.sh -b x-boot-bpir64-emmc -r x-aarch64/images -t emmc bananapi-bpi-r64
+```
diff --git a/board/aarch64/bananapi-bpi-r64/banana_pi_bpi-r64_interface.jpg b/board/aarch64/bananapi-bpi-r64/banana_pi_bpi-r64_interface.jpg
new file mode 100644
index 000000000..b99136c8f
Binary files /dev/null and b/board/aarch64/bananapi-bpi-r64/banana_pi_bpi-r64_interface.jpg differ
diff --git a/board/aarch64/bananapi-bpi-r64/bananapi-bpi-r64.mk b/board/aarch64/bananapi-bpi-r64/bananapi-bpi-r64.mk
new file mode 100644
index 000000000..deef167fd
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/bananapi-bpi-r64.mk
@@ -0,0 +1,35 @@
+define BANANAPI_BPI_R64_LINUX_CONFIG_FIXUPS
+ $(call KCONFIG_ENABLE_OPT,CONFIG_ARCH_MEDIATEK)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_MACH_MT7622)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_PINCTRL_MT7622)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_SERIAL_8250_MT6577)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_MTK_UART)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_MEDIATEK_WATCHDOG)
+ # Ethernet subsystem clock controller — required for the eth MAC,
+ # MT7531 DSA switch, and HSDMA to get their clocks from ðsys.
+ # Without this, eth probe fails and the switch is never detected.
+ $(call KCONFIG_ENABLE_OPT,CONFIG_COMMON_CLK_MT7622_ETHSYS)
+ # HIF subsystem clock controller — required for PCIe and USB.
+ $(call KCONFIG_ENABLE_OPT,CONFIG_COMMON_CLK_MT7622_HIFSYS)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_MEDIATEK_GE_PHY)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_REALTEK_PHY)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_NET_VENDOR_MEDIATEK)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_NET_MEDIATEK_SOC)
+ $(call KCONFIG_SET_OPT,CONFIG_NET_DSA_MT7530,m)
+ $(call KCONFIG_SET_OPT,CONFIG_MT7603E,m)
+ $(call KCONFIG_SET_OPT,CONFIG_PCIE_MEDIATEK,m)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_MMC_MTK)
+ $(call KCONFIG_SET_OPT,CONFIG_USB_XHCI_MTK,m)
+ $(call KCONFIG_SET_OPT,CONFIG_PHY_MTK_TPHY,m)
+ $(call KCONFIG_SET_OPT,CONFIG_MTK_THERMAL,m)
+ $(call KCONFIG_SET_OPT,CONFIG_MTK_SOC_THERMAL,m)
+ $(call KCONFIG_SET_OPT,CONFIG_I2C_MT65XX,m)
+ $(call KCONFIG_SET_OPT,CONFIG_PWM_MEDIATEK,m)
+ $(call KCONFIG_SET_OPT,CONFIG_REGULATOR_MT6380,m)
+ $(call KCONFIG_SET_OPT,CONFIG_NVMEM_MTK_EFUSE,m)
+ $(call KCONFIG_SET_OPT,CONFIG_CRYPTO_DEV_SAFEXCEL,m)
+ $(call KCONFIG_ENABLE_OPT,CONFIG_RTC_DRV_MT7622)
+endef
+
+$(eval $(ix-board))
+$(eval $(generic-package))
diff --git a/board/aarch64/bananapi-bpi-r64/bpi-r64-sw1.png b/board/aarch64/bananapi-bpi-r64/bpi-r64-sw1.png
new file mode 100644
index 000000000..381d92530
Binary files /dev/null and b/board/aarch64/bananapi-bpi-r64/bpi-r64-sw1.png differ
diff --git a/board/aarch64/bananapi-bpi-r64/debug-uart.png b/board/aarch64/bananapi-bpi-r64/debug-uart.png
new file mode 100644
index 000000000..edd0bd755
Binary files /dev/null and b/board/aarch64/bananapi-bpi-r64/debug-uart.png differ
diff --git a/board/aarch64/bananapi-bpi-r64/dts/Makefile b/board/aarch64/bananapi-bpi-r64/dts/Makefile
new file mode 100644
index 000000000..7f7e51f82
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/dts/Makefile
@@ -0,0 +1 @@
+dtb-y += mediatek/mt7622-bananapi-bpi-r64.dtb
diff --git a/board/aarch64/bananapi-bpi-r64/dts/mediatek/mt7622-bananapi-bpi-r64.dts b/board/aarch64/bananapi-bpi-r64/dts/mediatek/mt7622-bananapi-bpi-r64.dts
new file mode 100644
index 000000000..ea5f00c12
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/dts/mediatek/mt7622-bananapi-bpi-r64.dts
@@ -0,0 +1,3 @@
+#include
+
+#include "mt7622-bananapi-bpi-r64.dtsi"
diff --git a/board/aarch64/bananapi-bpi-r64/dts/mediatek/mt7622-bananapi-bpi-r64.dtsi b/board/aarch64/bananapi-bpi-r64/dts/mediatek/mt7622-bananapi-bpi-r64.dtsi
new file mode 100644
index 000000000..b279fc703
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/dts/mediatek/mt7622-bananapi-bpi-r64.dtsi
@@ -0,0 +1,10 @@
+/ {
+ chosen {
+ infix {
+ /* Default admin user password: 'admin' */
+ factory-password-hash = "$5$mI/zpOAqZYKLC2WU$i7iPzZiIjOjrBF3NyftS9CCq8dfYwHwrmUK097Jca9A";
+ usb-ports = <&ssusb>;
+ usb-port-names = "USB";
+ };
+ };
+};
diff --git a/board/aarch64/bananapi-bpi-r64/genimage.cfg.in b/board/aarch64/bananapi-bpi-r64/genimage.cfg.in
new file mode 100644
index 000000000..eda4fa136
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/genimage.cfg.in
@@ -0,0 +1,89 @@
+image cfg.ext4 {
+ empty = true
+ temporary = true
+ size = 128M
+ ext4 {
+ label = "cfg"
+ use-mke2fs = true
+ features = "uninit_bg"
+ extraargs = "-m 0 -i 4096"
+ }
+}
+
+# The /var partition will be expanded automatically at first boot
+# to use the full size of the SD-card or eMMC media.
+image var.ext4 {
+ empty = true
+ temporary = true
+ size = 128M
+ ext4 {
+ label = "var"
+ use-mke2fs = true
+ features = "uninit_bg"
+ extraargs = "-m 0 -i 4096"
+ }
+}
+
+image #INFIX_ID##VERSION#-bpi-r64-#TARGET#.img {
+ hdimage {
+ partition-table-type = "hybrid"
+ # MT7622 TF-A partition driver detects GPT by checking MBR[0]
+ # for the 0xEE protective entry. Place it first so that BL2
+ # (with partition-type = 0x83) lands at MBR slot 1.
+ gpt-protective-first = true
+ }
+
+ # BL2 bootloader at sector 1024 (0x80000). The MT7622 Boot ROM scans
+ # the hybrid MBR for a bootable entry and loads BL2 from its offset.
+ # partition-type makes it visible in the MBR at slot 1 (slot 0 holds
+ # the 0xEE protective entry required by the TF-A partition driver).
+ partition bl2 {
+ partition-type = 0x83
+ image = "bl2.img"
+ offset = 1024s
+ size = 1024s
+ bootable = true
+ }
+
+ # Factory/calibration data at fixed offset
+ partition factory {
+ offset = 4608K
+ size = 2M
+ }
+
+ # FIP partition - BL31 + U-Boot
+ partition fip {
+ image = "fip.bin"
+ offset = 13312s
+ size = 4096s
+ }
+
+ partition aux {
+ partition-uuid = D4EF35A0-0652-45A1-B3DE-D63339C82035
+ image = "aux.ext4"
+ }
+
+ partition primary {
+ partition-type-uuid = 0FC63DAF-8483-4772-8E79-3D69D8477DE4
+ bootable = true
+ size = 250M
+ image = "rootfs.squashfs"
+ }
+
+ partition secondary {
+ partition-type-uuid = 0FC63DAF-8483-4772-8E79-3D69D8477DE4
+ bootable = true
+ size = 250M
+ image = "rootfs.squashfs"
+ }
+
+ partition cfg {
+ partition-uuid = 7aa497f0-73b5-47e5-b2ab-8752d8a48105
+ image = "cfg.ext4"
+ }
+
+ partition var {
+ partition-uuid = 8046A06A-E45A-4A14-A6AD-6684704A393F
+ image = "var.ext4"
+ }
+}
diff --git a/board/aarch64/bananapi-bpi-r64/rootfs/usr/share/product/bananapi,bpi-r64/etc/factory-config.cfg b/board/aarch64/bananapi-bpi-r64/rootfs/usr/share/product/bananapi,bpi-r64/etc/factory-config.cfg
new file mode 100644
index 000000000..bb9eb50ce
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/rootfs/usr/share/product/bananapi,bpi-r64/etc/factory-config.cfg
@@ -0,0 +1,437 @@
+{
+ "ieee802-dot1ab-lldp:lldp": {
+ "infix-lldp:enabled": true
+ },
+ "ietf-hardware:hardware": {
+ "component": [
+ {
+ "name": "USB",
+ "class": "infix-hardware:usb",
+ "state": {
+ "admin-state": "unlocked"
+ }
+ },
+ {
+ "name": "radio0",
+ "class": "infix-hardware:wifi",
+ "infix-hardware:wifi-radio": {
+ "country-code": "DE",
+ "band": "2.4GHz",
+ "channel": "auto"
+ }
+ }
+ ]
+ },
+ "ietf-interfaces:interfaces": {
+ "interface": [
+ {
+ "name": "br0",
+ "type": "infix-if-type:bridge",
+ "ietf-ip:ipv4": {
+ "address": [
+ {
+ "ip": "192.168.0.1",
+ "prefix-length": 24
+ }
+ ]
+ }
+ },
+ {
+ "name": "lan0",
+ "type": "infix-if-type:ethernet",
+ "ietf-ip:ipv6": {},
+ "infix-interfaces:bridge-port": {
+ "bridge": "br0"
+ }
+ },
+ {
+ "name": "lan1",
+ "type": "infix-if-type:ethernet",
+ "ietf-ip:ipv6": {},
+ "infix-interfaces:bridge-port": {
+ "bridge": "br0"
+ }
+ },
+ {
+ "name": "lan2",
+ "type": "infix-if-type:ethernet",
+ "ietf-ip:ipv6": {},
+ "infix-interfaces:bridge-port": {
+ "bridge": "br0"
+ }
+ },
+ {
+ "name": "lan3",
+ "type": "infix-if-type:ethernet",
+ "ietf-ip:ipv6": {},
+ "infix-interfaces:bridge-port": {
+ "bridge": "br0"
+ }
+ },
+ {
+ "name": "lo",
+ "type": "infix-if-type:loopback",
+ "ietf-ip:ipv4": {
+ "address": [
+ {
+ "ip": "127.0.0.1",
+ "prefix-length": 8
+ }
+ ]
+ },
+ "ietf-ip:ipv6": {
+ "address": [
+ {
+ "ip": "::1",
+ "prefix-length": 128
+ }
+ ]
+ }
+ },
+ {
+ "name": "wan",
+ "type": "infix-if-type:ethernet",
+ "ietf-ip:ipv4": {
+ "infix-dhcp-client:dhcp": {
+ "option": [
+ {
+ "id": "ntp-server"
+ },
+ {
+ "id": "broadcast"
+ },
+ {
+ "id": "domain"
+ },
+ {
+ "id": "hostname"
+ },
+ {
+ "id": "dns-server"
+ },
+ {
+ "id": "router"
+ },
+ {
+ "id": "netmask"
+ },
+ {
+ "id": "vendor-class",
+ "value": "Banana Pi BPI-R64"
+ }
+ ]
+ }
+ },
+ "ietf-ip:ipv6": {
+ "infix-dhcpv6-client:dhcp": {
+ "option": [
+ {
+ "id": "ntp-server"
+ },
+ {
+ "id": "client-fqdn"
+ },
+ {
+ "id": "domain-search"
+ },
+ {
+ "id": "dns-server"
+ }
+ ]
+ }
+ }
+ },
+ {
+ "name": "wifi0-ap",
+ "type": "infix-if-type:wifi",
+ "infix-interfaces:wifi": {
+ "radio": "radio0",
+ "access-point": {
+ "ssid": "Infix",
+ "security": {
+ "secret": "wifi"
+ }
+ }
+ },
+ "infix-interfaces:bridge-port": {
+ "bridge": "br0"
+ }
+ }
+ ]
+ },
+ "ietf-keystore:keystore": {
+ "asymmetric-keys": {
+ "asymmetric-key": [
+ {
+ "name": "genkey",
+ "public-key-format": "infix-crypto-types:ssh-public-key-format",
+ "public-key": "",
+ "private-key-format": "infix-crypto-types:rsa-private-key-format",
+ "cleartext-private-key": "",
+ "certificates": {}
+ }
+ ]
+ },
+ "symmetric-keys": {
+ "symmetric-key": [
+ {
+ "name": "wifi",
+ "cleartext-symmetric-key": "aW5maXhpbmZpeA==",
+ "key-format": "infix-crypto-types:passphrase-key-format"
+ }
+ ]
+ }
+ },
+ "ietf-netconf-acm:nacm": {
+ "enable-nacm": true,
+ "read-default": "permit",
+ "write-default": "permit",
+ "exec-default": "permit",
+ "groups": {
+ "group": [
+ {
+ "name": "admin",
+ "user-name": [
+ "admin"
+ ]
+ },
+ {
+ "name": "operator",
+ "user-name": []
+ },
+ {
+ "name": "guest",
+ "user-name": []
+ }
+ ]
+ },
+ "rule-list": [
+ {
+ "name": "admin-acl",
+ "group": [
+ "admin"
+ ],
+ "rule": [
+ {
+ "name": "permit-all",
+ "module-name": "*",
+ "access-operations": "*",
+ "action": "permit",
+ "comment": "Allow 'admin' group complete access to all operations and data."
+ }
+ ]
+ },
+ {
+ "name": "operator-acl",
+ "group": [
+ "operator"
+ ],
+ "rule": [
+ {
+ "name": "permit-system-rpcs",
+ "module-name": "ietf-system",
+ "rpc-name": "*",
+ "access-operations": "exec",
+ "action": "permit",
+ "comment": "Operators can reboot, shutdown, and set system time."
+ }
+ ]
+ },
+ {
+ "name": "guest-acl",
+ "group": [
+ "guest"
+ ],
+ "rule": [
+ {
+ "name": "deny-all-write+exec",
+ "module-name": "*",
+ "access-operations": "create update delete exec",
+ "action": "deny",
+ "comment": "Guests cannot change anything or exec rpcs."
+ }
+ ]
+ },
+ {
+ "name": "default-deny-all",
+ "group": [
+ "*"
+ ],
+ "rule": [
+ {
+ "name": "deny-password-access",
+ "path": "/ietf-system:system/authentication/user/password",
+ "access-operations": "*",
+ "action": "deny",
+ "comment": "No user except admins can access password hashes."
+ },
+ {
+ "name": "deny-keystore-access",
+ "module-name": "ietf-keystore",
+ "access-operations": "*",
+ "action": "deny",
+ "comment": "No user except admins can access cryptographic keys."
+ },
+ {
+ "name": "deny-truststore-access",
+ "module-name": "ietf-truststore",
+ "access-operations": "*",
+ "action": "deny",
+ "comment": "No user except admins can access trust store."
+ }
+ ]
+ }
+ ]
+ },
+ "ietf-netconf-server:netconf-server": {
+ "listen": {
+ "endpoints": {
+ "endpoint": [
+ {
+ "name": "default-ssh",
+ "ssh": {
+ "tcp-server-parameters": {
+ "local-bind": [
+ {
+ "local-address": "::"
+ }
+ ]
+ },
+ "ssh-server-parameters": {
+ "server-identity": {
+ "host-key": [
+ {
+ "name": "default-key",
+ "public-key": {
+ "central-keystore-reference": "genkey"
+ }
+ }
+ ]
+ }
+ }
+ }
+ }
+ ]
+ }
+ }
+ },
+ "ietf-system:system": {
+ "hostname": "bpi-%m",
+ "ntp": {
+ "server": [
+ {
+ "name": "default",
+ "udp": {
+ "address": "pool.ntp.org"
+ }
+ }
+ ]
+ },
+ "authentication": {
+ "user": [
+ {
+ "name": "admin",
+ "password": "$factory$",
+ "infix-system:shell": "bash"
+ }
+ ]
+ },
+ "infix-system:motd-banner": "Li0tLS0tLS0uCnwgIC4gLiAgfCBJbmZpeCBPUyDigJQgSW1tdXRhYmxlLkZyaWVuZGx5LlNlY3VyZQp8LS4gdiAuLXwgaHR0cHM6Ly9rZXJuZWxraXQub3JnCictJy0tLSctJwo="
+ },
+ "infix-dhcp-server:dhcp-server": {
+ "option": [
+ {
+ "id": "ntp-server",
+ "address": "auto"
+ },
+ {
+ "id": "dns-server",
+ "address": "auto"
+ },
+ {
+ "id": "router",
+ "address": "auto"
+ }
+ ],
+ "subnet": [
+ {
+ "subnet": "192.168.0.0/24",
+ "pool": {
+ "start-address": "192.168.0.100",
+ "end-address": "192.168.0.250"
+ }
+ }
+ ]
+ },
+ "infix-firewall:firewall": {
+ "default": "wan",
+ "zone": [
+ {
+ "name": "lan",
+ "action": "accept",
+ "interface": [
+ "br0"
+ ]
+ },
+ {
+ "name": "wan",
+ "action": "drop",
+ "interface": [
+ "wan"
+ ],
+ "service": [
+ "dhcpv6-client"
+ ]
+ }
+ ],
+ "policy": [
+ {
+ "name": "lan-to-wan",
+ "action": "accept",
+ "ingress": [
+ "lan"
+ ],
+ "egress": [
+ "wan"
+ ],
+ "masquerade": true
+ }
+ ]
+ },
+ "infix-meta:meta": {
+ "version": "1.7"
+ },
+ "infix-services:mdns": {
+ "enabled": true
+ },
+ "infix-services:ssh": {
+ "enabled": true,
+ "hostkey": [
+ "genkey"
+ ],
+ "listen": [
+ {
+ "name": "ipv4",
+ "address": "0.0.0.0",
+ "port": 22
+ },
+ {
+ "name": "ipv6",
+ "address": "::",
+ "port": 22
+ }
+ ]
+ },
+ "infix-services:web": {
+ "enabled": true,
+ "console": {
+ "enabled": true
+ },
+ "netbrowse": {
+ "enabled": true
+ },
+ "restconf": {
+ "enabled": true
+ }
+ }
+}
diff --git a/board/aarch64/bananapi-bpi-r64/rootfs/usr/share/product/bananapi,bpi-r64/etc/udev/rules.d/90-bpi-r64-rename-ethernet.rules b/board/aarch64/bananapi-bpi-r64/rootfs/usr/share/product/bananapi,bpi-r64/etc/udev/rules.d/90-bpi-r64-rename-ethernet.rules
new file mode 100644
index 000000000..54ab4192d
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/rootfs/usr/share/product/bananapi,bpi-r64/etc/udev/rules.d/90-bpi-r64-rename-ethernet.rules
@@ -0,0 +1,12 @@
+# Rename MT7531 DSA switch ports by DT node path.
+# The kernel may name them by global port index (e.g. lan118) rather than
+# by DTS label, so match on OF_FULLNAME which is stable and independent
+# of how the kernel chose the initial interface name.
+#
+# MT7622 / BPI-R64 switch topology (switch@1f, ports):
+# port@0 = wan, port@1..4 = lan0..lan3, port@5,6 = cpu (not renamed)
+ACTION=="add", SUBSYSTEM=="net", ENV{OF_FULLNAME}=="*/switch@1f/ports/port@0", NAME="wan"
+ACTION=="add", SUBSYSTEM=="net", ENV{OF_FULLNAME}=="*/switch@1f/ports/port@1", NAME="lan0"
+ACTION=="add", SUBSYSTEM=="net", ENV{OF_FULLNAME}=="*/switch@1f/ports/port@2", NAME="lan1"
+ACTION=="add", SUBSYSTEM=="net", ENV{OF_FULLNAME}=="*/switch@1f/ports/port@3", NAME="lan2"
+ACTION=="add", SUBSYSTEM=="net", ENV{OF_FULLNAME}=="*/switch@1f/ports/port@4", NAME="lan3"
diff --git a/board/aarch64/bananapi-bpi-r64/uboot/emmc-extras.config b/board/aarch64/bananapi-bpi-r64/uboot/emmc-extras.config
new file mode 100644
index 000000000..9dff8112a
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/uboot/emmc-extras.config
@@ -0,0 +1,2 @@
+CONFIG_DEVICE_TREE_INCLUDES="infix-env.dtsi infix-key.dtsi mt7622-emmc-env.dtsi"
+CONFIG_SUPPORT_EMMC_BOOT=y
diff --git a/board/aarch64/bananapi-bpi-r64/uboot/extras.config b/board/aarch64/bananapi-bpi-r64/uboot/extras.config
new file mode 100644
index 000000000..232d4ea11
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/uboot/extras.config
@@ -0,0 +1,19 @@
+CONFIG_AUTOBOOT=y
+CONFIG_BOOTDELAY=2
+# CONFIG_MMC_PCI is not set
+CONFIG_ENV_IS_NOWHERE=y
+# CONFIG_ENV_IS_IN_MMC is not set
+
+CONFIG_USB=y
+CONFIG_USB_XHCI_HCD=y
+CONFIG_USB_XHCI_MTK=y
+CONFIG_PHY=y
+CONFIG_PHY_MTK_TPHY=y
+
+CONFIG_DM_MDIO=y
+CONFIG_DM_ETH_PHY=y
+CONFIG_PHY_ETHERNET_ID=y
+
+CONFIG_CMD_MDIO=y
+CONFIG_CMD_USB=y
+CONFIG_CMD_DM=y
diff --git a/board/aarch64/bananapi-bpi-r64/uboot/mt7622-emmc-env.dtsi b/board/aarch64/bananapi-bpi-r64/uboot/mt7622-emmc-env.dtsi
new file mode 100644
index 000000000..c70a826fb
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/uboot/mt7622-emmc-env.dtsi
@@ -0,0 +1,5 @@
+#include
+
+&env {
+ fdtfile = "mediatek/mt7622-bananapi-bpi-r64.dtb";
+};
diff --git a/board/aarch64/bananapi-bpi-r64/uboot/mt7622-env.dtsi b/board/aarch64/bananapi-bpi-r64/uboot/mt7622-env.dtsi
new file mode 100644
index 000000000..9f36845c6
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/uboot/mt7622-env.dtsi
@@ -0,0 +1,18 @@
+/ {
+ config {
+ env: environment {
+ bootcmd = "run ixboot";
+ boot_targets = "mmc0";
+ ethprime = "eth0";
+ fdt_addr_r = "0x43f00000";
+ kernel_addr_r = "0x44000000";
+ scriptaddr = "0x48000000";
+ ramdisk_addr_r = "0x4A000000";
+
+ /* This is a development platform, keep
+ * developer mode statically enabled.
+ */
+ ixbtn-devmode = "setenv dev_mode yes; echo Enabled";
+ };
+ };
+};
diff --git a/board/aarch64/bananapi-bpi-r64/uboot/mt7622-sd-env.dtsi b/board/aarch64/bananapi-bpi-r64/uboot/mt7622-sd-env.dtsi
new file mode 100644
index 000000000..45f3c86fe
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/uboot/mt7622-sd-env.dtsi
@@ -0,0 +1,6 @@
+#include
+
+&env {
+ boot_targets = "mmc1"; /* SD = mmc1 on MT7622 */
+ fdtfile = "mediatek/mt7622-bananapi-bpi-r64.dtb";
+};
diff --git a/board/aarch64/bananapi-bpi-r64/uboot/sd-extras.config b/board/aarch64/bananapi-bpi-r64/uboot/sd-extras.config
new file mode 100644
index 000000000..9502bd1d1
--- /dev/null
+++ b/board/aarch64/bananapi-bpi-r64/uboot/sd-extras.config
@@ -0,0 +1 @@
+CONFIG_DEVICE_TREE_INCLUDES="infix-env.dtsi infix-key.dtsi mt7622-sd-env.dtsi"
diff --git a/board/aarch64/raspberrypi-rpi64/genimage.cfg.in b/board/aarch64/raspberrypi-rpi64/genimage.cfg.in
index 8e7b356e8..88d7a580d 100644
--- a/board/aarch64/raspberrypi-rpi64/genimage.cfg.in
+++ b/board/aarch64/raspberrypi-rpi64/genimage.cfg.in
@@ -43,8 +43,8 @@ image #INFIX_ID##VERSION#-rpi64-sdcard.img {
partition boot {
partition-type = 0xc
- bootable = "true"
image = "boot.vfat"
+ bootable = "true"
}
partition aux {
@@ -54,16 +54,14 @@ image #INFIX_ID##VERSION#-rpi64-sdcard.img {
partition primary {
partition-type-uuid = linux
- bootable = "true"
- size = 250M
image = "rootfs.squashfs"
+ size = 250M
}
partition secondary {
partition-type-uuid = linux
- bootable = "true"
- size = 250M
image = "rootfs.squashfs"
+ size = 250M
}
partition cfg {
diff --git a/board/aarch64/raspberrypi-rpi64/rootfs/usr/share/product/raspberrypi,400 b/board/aarch64/raspberrypi-rpi64/rootfs/usr/share/product/raspberrypi,400
new file mode 120000
index 000000000..ef4c88cb8
--- /dev/null
+++ b/board/aarch64/raspberrypi-rpi64/rootfs/usr/share/product/raspberrypi,400
@@ -0,0 +1 @@
+raspberrypi,4-model-b
\ No newline at end of file
diff --git a/board/common/rootfs/usr/libexec/infix/init.d/10-sysctl-sync-ip-conf b/board/common/rootfs/usr/libexec/infix/init.d/10-sysctl-sync-ip-conf
index d2bcd2fa4..d1a0df3b1 100755
--- a/board/common/rootfs/usr/libexec/infix/init.d/10-sysctl-sync-ip-conf
+++ b/board/common/rootfs/usr/libexec/infix/init.d/10-sysctl-sync-ip-conf
@@ -5,24 +5,21 @@
# interfaces at boot, such that physical interfaces will start from
# the same point as virtual ones.
tmp=$(mktemp)
-fil=$(mktemp)
+out=$(mktemp)
# Ignore unreadable entries, like net.ipv6.conf.default.stable_secret
sysctl net.ipv4.conf.default >"$tmp" 2>/dev/null
sysctl net.ipv6.conf.default >>"$tmp" 2>/dev/null
-# Filter out read-only entries like net.ipv4.conf.default.mc_forwarding
-# to prevent misleading error messages in syslog
-while IFS= read -r line; do
- entry=$(echo "$line" | awk '{print $1}')
- path="/proc/sys/$(echo "$entry" | tr . /)"
- if [ -w "$path" ]; then
- echo "$line" >> "$fil"
- fi
-done < "$tmp"
-
-for iface in $(ip -j link show | jq -r .[].ifname); do
- sed -e "s/.default./.${iface}./g" "$fil" | sysctl -q -p -
+# Build a single sysctl input with settings for all interfaces
+for dir in /sys/class/net/*/; do
+ iface=${dir%/}
+ iface=${iface##*/}
+ sed "s/.default./.${iface}./g" "$tmp" >> "$out"
done
-rm "$tmp" "$fil"
+# Apply all at once, suppress errors from read-only entries
+# (e.g., net.ipv4.conf.*.mc_forwarding)
+sysctl -q -p - < "$out" 2>/dev/null
+
+rm "$tmp" "$out"
diff --git a/board/common/rootfs/usr/libexec/infix/mnt b/board/common/rootfs/usr/libexec/infix/mnt
index 4421613f3..dfe732fb2 100755
--- a/board/common/rootfs/usr/libexec/infix/mnt
+++ b/board/common/rootfs/usr/libexec/infix/mnt
@@ -59,17 +59,9 @@ is_mmc()
{
[ -n "$mmc" ] && return $mmc
- # Check if primary or secondary partition (our rootfs) is on MMC
- for label in primary secondary; do
- devname=$(find_partition_by_label "$label" 2>/dev/null)
- if [ -n "$devname" ]; then
- case "$devname" in
- mmcblk*)
- mmc=0
- return 0
- ;;
- esac
- fi
+ # Fast sysfs check — avoids triggering the slow partition scan
+ for d in /sys/class/block/mmcblk[0-9]; do
+ [ -d "$d" ] && mmc=0 && return 0
done
mmc=1
@@ -78,78 +70,68 @@ is_mmc()
wait_mmc()
{
- # Try up to 50 times with 0.2s sleep = 10 second timeout
- for _ in $(seq 50); do
- if ls /dev/mmcblk* >/dev/null 2>&1; then
- logger $opt -p user.notice -t "$nm" "MMC device available after delay"
- return 0
- fi
- sleep .2
+ tries=50
+ while [ $tries -gt 0 ]; do
+ for d in /dev/mmcblk[0-9]; do
+ if [ -b "$d" ]; then
+ logger $opt -p user.notice -t "$nm" "MMC device available after delay"
+ return 0
+ fi
+ done
+ sleep .2
+ tries=$((tries - 1))
done
logger $opt -p user.warn -t "$nm" "Timeout waiting for MMC device"
return 1
}
-# This early on we don't have the luxury of /dev/disk/by-label/$1
+# Read filesystem label from an ext2/3/4 formatted whole disk.
+# Superblock is at byte 1024, magic 0xEF53 at offset 56, label at 120.
+# Handles both LE and BE byte order (bi-endian MIPS, etc.)
+read_ext_label()
+{
+ magic=$(dd if="$1" bs=1 skip=1080 count=2 2>/dev/null \
+ | od -t x2 -An | tr -d ' \n')
+ case "$magic" in
+ ef53|53ef) ;;
+ *) return 1 ;;
+ esac
+
+ dd if="$1" bs=1 skip=1144 count=16 2>/dev/null | tr -d '\000'
+}
+
+# Look up a block device by its GPT partition name using the kernel's
+# sysfs uevent data (zero forks). Falls back to reading the ext2/3/4
+# superblock for whole disks without GPT (e.g., virtual or USB setups).
find_partition_by_label()
{
- label="$1"
+ # The kernel exposes GPT partition names as PARTNAME in uevent
+ for uevent in /sys/class/block/*/uevent; do
+ while IFS='=' read -r key val; do
+ if [ "$key" = "PARTNAME" ]; then
+ if [ "$val" = "$1" ]; then
+ devname="${uevent%/uevent}"
+ echo "${devname##*/}"
+ return 0
+ fi
+ break
+ fi
+ done < "$uevent"
+ done
+ # Fallback: ext filesystem label on whole disk
for diskpath in /sys/class/block/*; do
- devname=$(basename "$diskpath")
-
- # Skip partitions, only check whole disks
[ -f "$diskpath/partition" ] && continue
-
- # Skip ram, loop, and other virtual devices
+ devname="${diskpath##*/}"
case "$devname" in
- ram*|loop*|nullb*|dm-*) continue ;;
+ ram*|loop*|nullb*|dm-*|*boot[0-9]*|*rpmb) continue ;;
esac
-
- disk="/dev/$devname"
-
- #
- # 1. Try GPT/MBR partition label using sgdisk
- #
- result=$(sgdisk -p "$disk" 2>/dev/null | awk -v label="$label" -v devname="$devname" '
- /^ *[0-9]/ {
- if ($7 == label) {
- if (devname ~ /^(mmcblk|nvme|loop)/)
- print devname "p" $1;
- else
- print devname $1;
- exit 0;
- }
- }
- ')
-
- if [ -n "$result" ]; then
- echo "$result"
+ fslabel=$(read_ext_label "/dev/$devname")
+ if [ "$fslabel" = "$1" ]; then
+ echo "$devname"
return 0
fi
-
- #
- # 2. Fallback: Check if the whole disk is an ext4/ext2/ext3 filesystem
- #
-
- # Check for ext4/ext2/ext3 magic number (0xEF53) at offset 1080 (1024+56).
- magic_number=$(dd if="$disk" bs=1 skip=1080 count=2 2>/dev/null | od -t x2 -A n | tr -d ' \n')
-
- # Check for both Little-Endian ('53ef') and Big-Endian ('ef53') interpretations of 0xEF53.
- # This supports bi-endian architectures like MIPS that may run in BE mode,
- # as well as the LE mode which is standard for RISC-V and ext filesystems.
- if [ "$magic_number" = "ef53" ] || [ "$magic_number" = "53ef" ]; then
-
- # Read the volume label from offset 1144 (1024+120)
- fslabel=$(dd if="$disk" bs=1 skip=1144 count=16 2>/dev/null | tr -d '\000')
- logger $opt -p user.notice -t "$nm" "Found label $fslabel on disk $disk ..."
-
- if [ "$fslabel" = "$label" ]; then
- echo "$devname"
- return 0
- fi
- fi
done
return 1
@@ -319,12 +301,6 @@ mount_rw()
fi
fi
- # TODO: Also look for UBI partitions
-
- # Disable periodic fsck, yet keeping safety checks on ext4
- if grep "LABEL=$label" /etc/fstab |grep -q ext4; then
- tune2fs -c 0 -i 0 LABEL="$1" 2>/dev/null
- fi
mount LABEL="$1" 2>/dev/null && return 0
return 1
diff --git a/buildroot b/buildroot
index 7323ef2c8..48dfe8686 160000
--- a/buildroot
+++ b/buildroot
@@ -1 +1 @@
-Subproject commit 7323ef2c854ea332cf71735a3f97c4f0a519d9e6
+Subproject commit 48dfe8686849029d8ebffd80e9c21f87552b3f06
diff --git a/configs/aarch64_defconfig b/configs/aarch64_defconfig
index e95fc9404..84875f100 100644
--- a/configs/aarch64_defconfig
+++ b/configs/aarch64_defconfig
@@ -135,6 +135,7 @@ BR2_PACKAGE_HOST_UBOOT_TOOLS_FIT_SIGNATURE_SUPPORT=y
BR2_PACKAGE_HOST_UBOOT_TOOLS_FDT_ADD_PUBKEY=y
BR2_PACKAGE_ALDER_ALDER=y
BR2_PACKAGE_BANANAPI_BPI_R3=y
+BR2_PACKAGE_BANANAPI_BPI_R64=y
BR2_PACKAGE_FRIENDLYARM_NANOPI_R2S=y
BR2_PACKAGE_MARVELL_CN9130_CRB=y
BR2_PACKAGE_MARVELL_ESPRESSOBIN=y
diff --git a/configs/aarch64_minimal_defconfig b/configs/aarch64_minimal_defconfig
index 15f8017f3..b07b470da 100644
--- a/configs/aarch64_minimal_defconfig
+++ b/configs/aarch64_minimal_defconfig
@@ -113,6 +113,7 @@ BR2_PACKAGE_HOST_UBOOT_TOOLS_FIT_SIGNATURE_SUPPORT=y
BR2_PACKAGE_HOST_UBOOT_TOOLS_FDT_ADD_PUBKEY=y
BR2_PACKAGE_ALDER_ALDER=y
BR2_PACKAGE_BANANAPI_BPI_R3=y
+BR2_PACKAGE_BANANAPI_BPI_R64=y
BR2_PACKAGE_FRIENDLYARM_NANOPI_R2S=y
BR2_PACKAGE_MARVELL_CN9130_CRB=y
BR2_PACKAGE_MARVELL_ESPRESSOBIN=y
diff --git a/configs/bpi_r64_emmc_boot_defconfig b/configs/bpi_r64_emmc_boot_defconfig
new file mode 100644
index 000000000..425971894
--- /dev/null
+++ b/configs/bpi_r64_emmc_boot_defconfig
@@ -0,0 +1,42 @@
+BR2_aarch64=y
+BR2_TOOLCHAIN_EXTERNAL=y
+BR2_TOOLCHAIN_EXTERNAL_BOOTLIN=y
+BR2_DL_DIR="$(BR2_EXTERNAL_INFIX_PATH)/dl"
+BR2_CCACHE=y
+BR2_CCACHE_DIR="$(BR2_EXTERNAL_INFIX_PATH)/.ccache"
+BR2_ENABLE_DEBUG=y
+BR2_PACKAGE_OVERRIDE_FILE="$(BR2_EXTERNAL_INFIX_PATH)/local.mk"
+BR2_GLOBAL_PATCH_DIR="$(BR2_EXTERNAL_INFIX_PATH)/patches"
+BR2_SSP_NONE=y
+BR2_INIT_NONE=y
+BR2_SYSTEM_BIN_SH_NONE=y
+# BR2_PACKAGE_BUSYBOX is not set
+# BR2_PACKAGE_IFUPDOWN_SCRIPTS is not set
+# BR2_TARGET_ROOTFS_TAR is not set
+BR2_TARGET_ARM_TRUSTED_FIRMWARE=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_CUSTOM_GIT=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_CUSTOM_REPO_URL="https://github.com/mtk-openwrt/arm-trusted-firmware-mtk.git"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_CUSTOM_REPO_VERSION="78a0dfd927bb00ce973a1f8eb4079df0f755887a"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_PLATFORM="mt7622"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_FIP=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_UBOOT_AS_BL33=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_ADDITIONAL_VARIABLES="BOOT_DEVICE=emmc DDR3_FLYBY=1 DEVICE_HEADER_OFFSET=0x0 USE_MKIMAGE=1"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_IMAGES="*.img *.bin"
+BR2_TARGET_UBOOT=y
+BR2_TARGET_UBOOT_BUILD_SYSTEM_KCONFIG=y
+BR2_TARGET_UBOOT_CUSTOM_VERSION=y
+BR2_TARGET_UBOOT_CUSTOM_VERSION_VALUE="2025.01"
+BR2_TARGET_UBOOT_BOARD_DEFCONFIG="mt7622_bpir64_emmc"
+BR2_TARGET_UBOOT_CONFIG_FRAGMENT_FILES="${BR2_EXTERNAL_INFIX_PATH}/board/common/uboot/extras.config ${BR2_EXTERNAL_INFIX_PATH}/board/aarch64/bananapi-bpi-r64/uboot/extras.config ${BR2_EXTERNAL_INFIX_PATH}/board/aarch64/bananapi-bpi-r64/uboot/emmc-extras.config"
+BR2_TARGET_UBOOT_NEEDS_DTC=y
+BR2_TARGET_UBOOT_FORMAT_DTB=y
+BR2_TARGET_UBOOT_CUSTOM_DTS_PATH="${BR2_EXTERNAL_INFIX_PATH}/board/aarch64/bananapi-bpi-r64/uboot/*.dtsi"
+BR2_PACKAGE_HOST_BMAP_TOOLS=y
+BR2_PACKAGE_HOST_GENIMAGE=y
+BR2_PACKAGE_HOST_RAUC=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS_FIT_SUPPORT=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS_FIT_SIGNATURE_SUPPORT=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS_FDT_ADD_PUBKEY=y
+TRUSTED_KEYS=y
+TRUSTED_KEYS_DEVELOPMENT=y
diff --git a/configs/bpi_r64_sd_boot_defconfig b/configs/bpi_r64_sd_boot_defconfig
new file mode 100644
index 000000000..56f5f2acb
--- /dev/null
+++ b/configs/bpi_r64_sd_boot_defconfig
@@ -0,0 +1,42 @@
+BR2_aarch64=y
+BR2_TOOLCHAIN_EXTERNAL=y
+BR2_TOOLCHAIN_EXTERNAL_BOOTLIN=y
+BR2_DL_DIR="$(BR2_EXTERNAL_INFIX_PATH)/dl"
+BR2_CCACHE=y
+BR2_CCACHE_DIR="$(BR2_EXTERNAL_INFIX_PATH)/.ccache"
+BR2_ENABLE_DEBUG=y
+BR2_PACKAGE_OVERRIDE_FILE="$(BR2_EXTERNAL_INFIX_PATH)/local.mk"
+BR2_GLOBAL_PATCH_DIR="$(BR2_EXTERNAL_INFIX_PATH)/patches"
+BR2_SSP_NONE=y
+BR2_INIT_NONE=y
+BR2_SYSTEM_BIN_SH_NONE=y
+# BR2_PACKAGE_BUSYBOX is not set
+# BR2_PACKAGE_IFUPDOWN_SCRIPTS is not set
+# BR2_TARGET_ROOTFS_TAR is not set
+BR2_TARGET_ARM_TRUSTED_FIRMWARE=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_CUSTOM_GIT=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_CUSTOM_REPO_URL="https://github.com/mtk-openwrt/arm-trusted-firmware-mtk.git"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_CUSTOM_REPO_VERSION="78a0dfd927bb00ce973a1f8eb4079df0f755887a"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_PLATFORM="mt7622"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_FIP=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_UBOOT_AS_BL33=y
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_ADDITIONAL_VARIABLES="BOOT_DEVICE=sdmmc DDR3_FLYBY=1 DEVICE_HEADER_OFFSET=0x80000 USE_MKIMAGE=1"
+BR2_TARGET_ARM_TRUSTED_FIRMWARE_IMAGES="*.img *.bin"
+BR2_TARGET_UBOOT=y
+BR2_TARGET_UBOOT_BUILD_SYSTEM_KCONFIG=y
+BR2_TARGET_UBOOT_CUSTOM_VERSION=y
+BR2_TARGET_UBOOT_CUSTOM_VERSION_VALUE="2025.01"
+BR2_TARGET_UBOOT_BOARD_DEFCONFIG="mt7622_bpir64_sd"
+BR2_TARGET_UBOOT_CONFIG_FRAGMENT_FILES="${BR2_EXTERNAL_INFIX_PATH}/board/common/uboot/extras.config ${BR2_EXTERNAL_INFIX_PATH}/board/aarch64/bananapi-bpi-r64/uboot/extras.config ${BR2_EXTERNAL_INFIX_PATH}/board/aarch64/bananapi-bpi-r64/uboot/sd-extras.config"
+BR2_TARGET_UBOOT_NEEDS_DTC=y
+BR2_TARGET_UBOOT_FORMAT_DTB=y
+BR2_TARGET_UBOOT_CUSTOM_DTS_PATH="${BR2_EXTERNAL_INFIX_PATH}/board/aarch64/bananapi-bpi-r64/uboot/*.dtsi"
+BR2_PACKAGE_HOST_BMAP_TOOLS=y
+BR2_PACKAGE_HOST_GENIMAGE=y
+BR2_PACKAGE_HOST_RAUC=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS_FIT_SUPPORT=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS_FIT_SIGNATURE_SUPPORT=y
+BR2_PACKAGE_HOST_UBOOT_TOOLS_FDT_ADD_PUBKEY=y
+TRUSTED_KEYS=y
+TRUSTED_KEYS_DEVELOPMENT=y
diff --git a/doc/ChangeLog.md b/doc/ChangeLog.md
index 1550faa19..b632a3b5e 100644
--- a/doc/ChangeLog.md
+++ b/doc/ChangeLog.md
@@ -3,6 +3,19 @@ Change Log
All notable changes to the project are documented in this file.
+[v26.03.0][UNRELEASED]
+-------------------------
+
+### Changes
+
+- Add support for [Banana Pi R64 Mini][BPI-R64], 5 port router with WiFi 5
+
+### Fixes
+
+- N/A
+
+[BPI-R64]: https://docs.banana-pi.org/en/BPI-R64/BananaPi_BPI-R64
+
[v26.02.0][] - 2026-03-01
-------------------------
@@ -1932,6 +1945,7 @@ Supported YANG models in addition to those used by sysrepo and netopeer:
[buildroot]: https://buildroot.org/
[UNRELEASED]: https://github.com/kernelkit/infix/compare/v26.02.0...HEAD
+[v26.03.0]: https://github.com/kernelkit/infix/compare/v26.02.0...v26.03.0
[v26.02.0]: https://github.com/kernelkit/infix/compare/v26.01.0...v26.02.0
[v26.01.0]: https://github.com/kernelkit/infix/compare/v25.11.0...v26.01.0
[v25.11.0]: https://github.com/kernelkit/infix/compare/v25.10.0...v25.11.0
diff --git a/package/feature-wifi/Config.in b/package/feature-wifi/Config.in
index d0a72aa8d..3306b49c7 100644
--- a/package/feature-wifi/Config.in
+++ b/package/feature-wifi/Config.in
@@ -20,6 +20,7 @@ config BR2_PACKAGE_FEATURE_WIFI_MEDIATEK
select BR2_PACKAGE_LINUX_FIRMWARE
select BR2_PACKAGE_LINUX_FIRMWARE_MEDIATEK_MT7601U
select BR2_PACKAGE_LINUX_FIRMWARE_MEDIATEK_MT7610E
+ select BR2_PACKAGE_LINUX_FIRMWARE_MEDIATEK_MT7615
select BR2_PACKAGE_LINUX_FIRMWARE_MEDIATEK_MT76X2E
select BR2_PACKAGE_LINUX_FIRMWARE_MEDIATEK_MT7921
select BR2_PACKAGE_LINUX_FIRMWARE_MEDIATEK_MT7922
diff --git a/patches/genimage/0001-hdimage-put-GPT-protective-MBR-entry-first-in-hybrid.patch b/patches/genimage/0001-hdimage-put-GPT-protective-MBR-entry-first-in-hybrid.patch
new file mode 100644
index 000000000..2714e611f
--- /dev/null
+++ b/patches/genimage/0001-hdimage-put-GPT-protective-MBR-entry-first-in-hybrid.patch
@@ -0,0 +1,133 @@
+From 7f50533b9e57f5e7d1e4dd47c3f43e2d6a9c8b1a Mon Sep 17 00:00:00 2001
+From: Joachim Wiberg
+Date: Sun, 8 Mar 2026 04:33:56 +0100
+Subject: [PATCH] hdimage: add gpt-protective-first option for hybrid MBR
+Organization: Wires
+
+In a hybrid MBR the conventional layout (used by gdisk and others) is:
+
+ MBR[0] = 0xEE (GPT protective, covers whole disk)
+ MBR[1..3] = user-selected GPT partitions with legacy type codes
+
+genimage currently appends the 0xEE entry after the data partitions,
+producing the opposite order. This is fine for most platforms, but
+breaks firmware that detects GPT by inspecting only MBR entry 0: seeing
+a non-0xEE type there it falls into pure-MBR mode and cannot look up
+GPT partitions by name.
+
+The TF-A partition driver (drivers/partition/partition.c) exhibits
+exactly this behaviour: load_mbr_header() copies entry[0] and checks
+type == 0xEE to select between MBR and GPT mode. The MediaTek MT7622
+platform (BananaPi BPI-R64) is a concrete example where this matters.
+
+On the other hand, Raspberry Pi firmware scans all MBR slots for a
+bootable FAT32 partition. If slot 0 holds a 0xEE protective entry the
+firmware switches to GPT detection, looks for an EFI System Partition
+UUID, and reports "no bootable partitions" when none is found.
+
+Add an opt-in hdimage option `gpt-protective-first = true` that places
+the 0xEE entry at slot 0 and shifts data partitions to slots 1..3.
+The default (false) preserves the existing genimage behaviour so that
+platforms like Raspberry Pi continue to work without any changes.
+
+Signed-off-by: Joachim Wiberg
+---
+ README.rst | 10 ++++++++++
+ image-hd.c | 27 ++++++++++++++++++++++-----
+ 2 files changed, 32 insertions(+), 5 deletions(-)
+
+diff --git a/README.rst b/README.rst
+index 9a95f75..f45fb93 100644
+--- a/README.rst
++++ b/README.rst
+@@ -480,6 +480,16 @@ Options:
+ placed at 512 bytes (sector 1). Defaults to 1024 bytes (sector 2).
+ :gpt-no-backup: Boolean. If true, then the backup partition table at the end of
+ the image is not written.
++:gpt-protective-first: Boolean. If true, then for ``hybrid`` partition tables, the GPT
++ protective entry (type ``0xEE``) is placed at MBR slot 0 and
++ data partitions fill slots 1..3. This matches the layout
++ produced by tools such as gdisk and is required by firmware
++ that identifies GPT disks by inspecting only MBR entry 0 —
++ for example the TF-A partition driver used on MediaTek MT7622
++ (BananaPi BPI-R64). When false (the default), the 0xEE entry
++ is placed after the data partitions, which is compatible with
++ firmware that scans MBR slots for a bootable partition (e.g.
++ Raspberry Pi).
+ :disk-uuid: UUID string used as disk id in GPT partitioning. Defaults to a
+ random value.
+ :fill: If this is set to true, then the image file will be filled
+diff --git a/image-hd.c b/image-hd.c
+index 274c6ac..610d9d1 100644
+--- a/image-hd.c
++++ b/image-hd.c
+@@ -46,6 +46,7 @@ struct hdimage {
+ int table_type;
+ unsigned long long gpt_location;
+ cfg_bool_t gpt_no_backup;
++ cfg_bool_t gpt_protective_first;
+ cfg_bool_t fill;
+ unsigned long long file_size;
+ };
+@@ -152,6 +153,26 @@ static int hdimage_insert_mbr(struct image *image, struct list_head *partitions)
+ memset(&mbr, 0, sizeof(mbr));
+ memcpy(&mbr.disk_signature, &hd->disksig, sizeof(hd->disksig));
+
++ /*
++ * For hybrid MBR, optionally write the GPT protective entry (0xEE) at
++ * slot 0 first when gpt-protective-first = true. This matches the
++ * conventional layout used by tools such as gdisk and is required by
++ * firmware that detects GPT by inspecting only MBR[0] (e.g. the TF-A
++ * partition driver on MediaTek MT7622). Leave slot 0 free by default
++ * so that firmware scanning for a bootable MBR partition (e.g.
++ * Raspberry Pi) can find data partitions at slots 0..2.
++ */
++ if (hd->table_type == TYPE_HYBRID && hd->gpt_protective_first) {
++ struct mbr_partition_entry *entry = &mbr.part_entry[0];
++
++ entry->boot = 0x00;
++ entry->partition_type = 0xee;
++ entry->relative_sectors = 1;
++ entry->total_sectors = hd->gpt_location / 512 + GPT_SECTORS - 2;
++ hdimage_setup_chs(entry, 0);
++ i = 1;
++ }
++
+ list_for_each_entry(part, partitions, list) {
+ struct mbr_partition_entry *entry;
+
+@@ -176,13 +197,13 @@ static int hdimage_insert_mbr(struct image *image, struct list_head *partitions)
+ i++;
+ }
+
+- if (hd->table_type == TYPE_HYBRID) {
++ /* For hybrid MBR without gpt-protective-first, append 0xEE after data partitions. */
++ if (hd->table_type == TYPE_HYBRID && !hd->gpt_protective_first) {
+ struct mbr_partition_entry *entry;
+
+ entry = &mbr.part_entry[i];
+
+ entry->boot = 0x00;
+-
+ entry->partition_type = 0xee;
+ entry->relative_sectors = 1;
+ entry->total_sectors = hd->gpt_location / 512 + GPT_SECTORS - 2;
+@@ -978,6 +999,7 @@ static int hdimage_setup(struct image *image, cfg_t *cfg)
+ table_type = cfg_getstr(cfg, "partition-table-type");
+ hd->gpt_location = cfg_getint_suffix(cfg, "gpt-location");
+ hd->gpt_no_backup = cfg_getbool(cfg, "gpt-no-backup");
++ hd->gpt_protective_first = cfg_getbool(cfg, "gpt-protective-first");
+ hd->fill = cfg_getbool(cfg, "fill");
+
+ if (is_block_device(imageoutfile(image))) {
+@@ -1227,6 +1249,7 @@ static cfg_opt_t hdimage_opts[] = {
+ CFG_BOOL("gpt", cfg_false, CFGF_NODEFAULT),
+ CFG_STR("gpt-location", NULL, CFGF_NONE),
+ CFG_BOOL("gpt-no-backup", cfg_false, CFGF_NONE),
++ CFG_BOOL("gpt-protective-first", cfg_false, CFGF_NONE),
+ CFG_BOOL("fill", cfg_false, CFGF_NONE),
+ CFG_END()
+ };
+--
+2.43.0
+
diff --git a/patches/uboot/2025.01/0001-hush-Remove-Ctrl-C-detection-in-loops.patch b/patches/uboot/2025.01/0001-hush-Remove-Ctrl-C-detection-in-loops.patch
index ce9970206..5d4dca027 100644
--- a/patches/uboot/2025.01/0001-hush-Remove-Ctrl-C-detection-in-loops.patch
+++ b/patches/uboot/2025.01/0001-hush-Remove-Ctrl-C-detection-in-loops.patch
@@ -1,10 +1,7 @@
From 9a9885324c70d607c9c79814441dbc829e212e41 Mon Sep 17 00:00:00 2001
From: Tobias Waldekranz
Date: Mon, 10 Jun 2024 13:25:31 +0200
-Subject: [PATCH 1/7] hush: Remove Ctrl-C detection in loops
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
+Subject: [PATCH 1/9] hush: Remove Ctrl-C detection in loops
Organization: Wires
Assume that the original intent was to emulate SIGINT to a shell. This
@@ -17,7 +14,7 @@ Disable this behavior and delegate the problem of loop termination to
the writer of the script instead.
Signed-off-by: Tobias Waldekranz
-Signed-off-by: Mattias Walström
+Signed-off-by: Joachim Wiberg
---
common/cli_hush.c | 7 -------
1 file changed, 7 deletions(-)
diff --git a/patches/uboot/2025.01/0002-cmd-new-command-rpidisplay.patch b/patches/uboot/2025.01/0002-cmd-new-command-rpidisplay.patch
index 9594f4433..52becdcd2 100644
--- a/patches/uboot/2025.01/0002-cmd-new-command-rpidisplay.patch
+++ b/patches/uboot/2025.01/0002-cmd-new-command-rpidisplay.patch
@@ -1,13 +1,14 @@
From 7efc3aa61fbc84b2c0c959e737257d2de2e8020c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Mattias=20Walstr=C3=B6m?=
Date: Sat, 6 Sep 2025 22:18:27 +0200
-Subject: [PATCH 2/7] cmd: new command rpidisplay
+Subject: [PATCH 2/9] cmd: new command rpidisplay
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Organization: Wires
Signed-off-by: Mattias Walström
+Signed-off-by: Joachim Wiberg
---
cmd/Kconfig | 14 ++++++++
cmd/Makefile | 2 +-
diff --git a/patches/uboot/2025.01/0003-arm-dts-at91-sama7g5ek-increase-clock-for-sdmmc-from.patch b/patches/uboot/2025.01/0003-arm-dts-at91-sama7g5ek-increase-clock-for-sdmmc-from.patch
index 0e96b9214..a8f183fd6 100644
--- a/patches/uboot/2025.01/0003-arm-dts-at91-sama7g5ek-increase-clock-for-sdmmc-from.patch
+++ b/patches/uboot/2025.01/0003-arm-dts-at91-sama7g5ek-increase-clock-for-sdmmc-from.patch
@@ -1,11 +1,8 @@
From c646eef3ee304ae49ad7e3f998ed08bfa0efb7b9 Mon Sep 17 00:00:00 2001
From: Mihai Sain
Date: Fri, 5 May 2023 13:28:31 +0300
-Subject: [PATCH 3/7] arm: dts: at91: sama7g5ek: increase clock for sdmmc from
+Subject: [PATCH 3/9] arm: dts: at91: sama7g5ek: increase clock for sdmmc from
25 MHz to 50 MHz
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
Organization: Wires
Current clock for sdmmc0 and sdmmc1 is 25 MHz because of the caps forced
@@ -16,7 +13,7 @@ improve the boot time when reading the kernel binary. Tested on
sama7g5ek rev 5 using mmcinfo command.
Signed-off-by: Mihai Sain
-Signed-off-by: Mattias Walström
+Signed-off-by: Joachim Wiberg
---
arch/arm/dts/at91-sama7g5ek.dts | 4 ----
1 file changed, 4 deletions(-)
diff --git a/patches/uboot/2025.01/0004-arm-dts-at91-sama7g5ek-supports-high-speed-on-mmc0-e.patch b/patches/uboot/2025.01/0004-arm-dts-at91-sama7g5ek-supports-high-speed-on-mmc0-e.patch
index 6bbef0563..9299166b7 100644
--- a/patches/uboot/2025.01/0004-arm-dts-at91-sama7g5ek-supports-high-speed-on-mmc0-e.patch
+++ b/patches/uboot/2025.01/0004-arm-dts-at91-sama7g5ek-supports-high-speed-on-mmc0-e.patch
@@ -1,11 +1,8 @@
From 5a530e4eebf64887fd6b449dd45df04eccd07cad Mon Sep 17 00:00:00 2001
From: Joachim Wiberg
Date: Thu, 12 Feb 2026 10:00:02 +0100
-Subject: [PATCH 4/7] arm: dts: at91: sama7g5ek supports high-speed on mmc0
+Subject: [PATCH 4/9] arm: dts: at91: sama7g5ek supports high-speed on mmc0
(eMMC)
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
Organization: Wires
- eMMC high-speed timing is supported
@@ -14,7 +11,6 @@ Organization: Wires
Tested on sama7g5ek rev 5.
Signed-off-by: Joachim Wiberg
-Signed-off-by: Mattias Walström
---
arch/arm/dts/at91-sama7g5ek.dts | 2 ++
1 file changed, 2 insertions(+)
diff --git a/patches/uboot/2025.01/0005-net-phy-Add-the-Airoha-EN8811H-PHY-driver.patch b/patches/uboot/2025.01/0005-net-phy-Add-the-Airoha-EN8811H-PHY-driver.patch
index 81e8eccc5..4261bcffe 100644
--- a/patches/uboot/2025.01/0005-net-phy-Add-the-Airoha-EN8811H-PHY-driver.patch
+++ b/patches/uboot/2025.01/0005-net-phy-Add-the-Airoha-EN8811H-PHY-driver.patch
@@ -1,10 +1,7 @@
From be250151366460ee318ca47bb15ec23e5e322a84 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Mattias=20Walstr=C3=B6m?=
Date: Wed, 18 Feb 2026 17:00:09 +0100
-Subject: [PATCH 5/7] net: phy: Add the Airoha EN8811H PHY driver
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
+Subject: [PATCH 5/9] net: phy: Add the Airoha EN8811H PHY driver
Organization: Wires
Add the driver for the Airoha EN8811H 2.5 Gigabit PHY. The PHY supports
@@ -26,7 +23,7 @@ I have modified the relevant process to align with the U-Boot boot sequence.
and have validated this on Banana Pi BPI-R3 Mini.
Signed-off-by: Lucien.Jheng
-Signed-off-by: Mattias Walström
+Signed-off-by: Joachim Wiberg
---
drivers/net/phy/Kconfig | 25 +
drivers/net/phy/Makefile | 1 +
diff --git a/patches/uboot/2025.01/0006-Add-bpi-r3-mini-device-tree.patch b/patches/uboot/2025.01/0006-Add-bpi-r3-mini-device-tree.patch
index 1811ce3c6..229e2200e 100644
--- a/patches/uboot/2025.01/0006-Add-bpi-r3-mini-device-tree.patch
+++ b/patches/uboot/2025.01/0006-Add-bpi-r3-mini-device-tree.patch
@@ -1,13 +1,10 @@
From a987f92a768291669eec1a8c5d413190bd9241ec Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Mattias=20Walstr=C3=B6m?=
Date: Wed, 18 Feb 2026 17:00:42 +0100
-Subject: [PATCH 6/7] Add bpi-r3-mini device tree
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
+Subject: [PATCH 6/9] Add bpi-r3-mini device tree
Organization: Wires
-Signed-off-by: Mattias Walström
+Signed-off-by: Joachim Wiberg
---
arch/arm/dts/Makefile | 1 +
arch/arm/dts/mt7986a-bpi-r3-mini.dts | 238 +++++++++++++++++++++++++++
diff --git a/patches/uboot/2025.01/0007-bpi-r3-r4-Add-probe-for-specific-model.patch b/patches/uboot/2025.01/0007-bpi-r3-r4-Add-probe-for-specific-model.patch
index a3e1bbe7a..1868e06c3 100644
--- a/patches/uboot/2025.01/0007-bpi-r3-r4-Add-probe-for-specific-model.patch
+++ b/patches/uboot/2025.01/0007-bpi-r3-r4-Add-probe-for-specific-model.patch
@@ -1,10 +1,7 @@
From 57b3cd8612a8da852f0796d97e6a7526cc4742cc Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Mattias=20Walstr=C3=B6m?=
Date: Wed, 18 Feb 2026 17:02:23 +0100
-Subject: [PATCH 7/7] bpi-r3/r4: Add probe for specific model
-MIME-Version: 1.0
-Content-Type: text/plain; charset=UTF-8
-Content-Transfer-Encoding: 8bit
+Subject: [PATCH 7/9] bpi-r3/r4: Add probe for specific model
Organization: Wires
Probe for bpi-r3 and bpi-r3-mini and select correct device tree,
@@ -12,7 +9,7 @@ prepare for bpi-r4 (not supported yet, but soon), for bpi-r3,
look if there are phys connected, if so it is a mini, else it is
regular bpi-r3.
-Signed-off-by: Mattias Walström
+Signed-off-by: Joachim Wiberg
---
arch/arm/mach-mediatek/Kconfig | 3 +
board/mediatek/mt7986/Kconfig | 10 ++
diff --git a/patches/uboot/2025.01/0008-arm-mediatek-fix-MT7622-BROM-image-header-type.patch b/patches/uboot/2025.01/0008-arm-mediatek-fix-MT7622-BROM-image-header-type.patch
new file mode 100644
index 000000000..f3eb471e8
--- /dev/null
+++ b/patches/uboot/2025.01/0008-arm-mediatek-fix-MT7622-BROM-image-header-type.patch
@@ -0,0 +1,37 @@
+From c07b984f00e48294cb6e14825919405d53532271 Mon Sep 17 00:00:00 2001
+From: Joachim Wiberg
+Date: Thu, 26 Feb 2026 11:22:28 +0100
+Subject: [PATCH 8/9] arm: mediatek: fix MT7622 BROM image header type
+Organization: Wires
+
+The LK image header for MT7622 was inadvertently changed to "media=nor"
+when board Kconfigs were merged into mach-mediatek/Kconfig. MT7622 uses
+the same ATF/LK-based boot flow as MT7623 and requires "lk=1" so that
+mkimage generates the correct header for the BROM to accept.
+
+Reported-by: Shiji Yang
+Signed-off-by: Joachim Wiberg
+---
+ arch/arm/mach-mediatek/Kconfig | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+diff --git a/arch/arm/mach-mediatek/Kconfig b/arch/arm/mach-mediatek/Kconfig
+index def8a564d90..53d5b5e58bd 100644
+--- a/arch/arm/mach-mediatek/Kconfig
++++ b/arch/arm/mach-mediatek/Kconfig
+@@ -148,10 +148,10 @@ config SYS_CONFIG_NAME
+
+ config MTK_BROM_HEADER_INFO
+ string
+- default "media=nor" if TARGET_MT8518 || TARGET_MT8512 || TARGET_MT7629 || TARGET_MT7622
++ default "media=nor" if TARGET_MT8518 || TARGET_MT8512 || TARGET_MT7629
+ default "media=emmc" if TARGET_MT8516 || TARGET_MT8365 || TARGET_MT8183
+ default "media=snand;nandinfo=2k+64" if TARGET_MT7981 || TARGET_MT7986 || TARGET_MT7988
+- default "lk=1" if TARGET_MT7623
++ default "lk=1" if TARGET_MT7622 || TARGET_MT7623
+
+ source "board/mediatek/mt7986/Kconfig"
+ source "board/mediatek/mt7988/Kconfig"
+--
+2.43.0
+
diff --git a/patches/uboot/2025.01/0009-arm-mediatek-add-BananaPi-BPI-R64-MT7622-defconfigs.patch b/patches/uboot/2025.01/0009-arm-mediatek-add-BananaPi-BPI-R64-MT7622-defconfigs.patch
new file mode 100644
index 000000000..d832763fd
--- /dev/null
+++ b/patches/uboot/2025.01/0009-arm-mediatek-add-BananaPi-BPI-R64-MT7622-defconfigs.patch
@@ -0,0 +1,710 @@
+From d89bb394f5d5f2cf8b15e5694d168f937b9ac426 Mon Sep 17 00:00:00 2001
+From: Joachim Wiberg
+Date: Thu, 26 Feb 2026 11:23:28 +0100
+Subject: [PATCH 9/9] arm: mediatek: add BananaPi BPI-R64 (MT7622) defconfigs
+Organization: Wires
+
+Add U-Boot support for the BananaPi BPI-R64 router board, based on the
+MediaTek MT7622 SoC (dual-core ARM Cortex-A53, 64-bit). Three defconfigs
+are provided, following the BPI-R3 pattern:
+
+ mt7622_bpir64_emmc_defconfig - eMMC (mmc0), env at 4 MiB
+ mt7622_bpir64_sd_defconfig - SD card (mmc1), env at 4 MiB
+ mt7622_bpir64_snand_defconfig - SPI NAND via SNFI, env in UBI
+
+All variants include PCIe, USB3 (xHCI + T-PHY), Ethernet (MT7531 switch
+via SGMII/2500base-x), GPIO-LEDs, and push-button support.
+
+The SNAND variant uses the upstream CONFIG_MTK_SNFI_SPI + MTD_SPI_NAND
+path with a spi-nand child under &snfi, adapting OpenWRT patch 403 to
+the upstream driver model (which has no separate &snand node or
+CONFIG_MTK_SPI_NAND). NAND layout: bl2 at 0x0 (512 KiB), ubi for the
+remainder of the flash.
+
+Also, add hardware description missing from the original device tree:
+ - ethernet0 alias for the MT7531 switch
+ - gpio-keys nodes for the reset (GPIO0) and WPS (GPIO102) buttons
+ - gpio-leds nodes for the green (GPIO89) and blue (GPIO85) LEDs
+ - Fix cap-sd-highspeed -> cap-mmc-highspeed on mmc0 (eMMC requires
+ the MMC-specific capability flag, not the SD one)
+ - Reduce mmc1 (SD card) max-frequency to 25 MHz for stability
+
+Sources:
+ OpenWRT patches 402-404/408 for package/boot/uboot-mediatek
+ https://git.infobricfleet.com/gtu/openwrt/-/tree/master/package/boot/uboot-mediatek/patches
+ Frank Wunderlich's initial MT7622/BPI-R64 U-Boot port (2019)
+ https://github.com/frank-w/u-boot/commit/c451ad3950e63d54b074f71e930459281dd3f594
+
+Signed-off-by: Joachim Wiberg
+---
+ arch/arm/dts/mt7622-bananapi-bpi-r64-nand.dts | 290 ++++++++++++++++++
+ arch/arm/dts/mt7622-bananapi-bpi-r64.dts | 38 ++-
+ board/mediatek/mt7622/MAINTAINERS | 5 +
+ configs/mt7622_bpir64_emmc_defconfig | 82 +++++
+ configs/mt7622_bpir64_sd_defconfig | 82 +++++
+ configs/mt7622_bpir64_snand_defconfig | 88 ++++++
+ 6 files changed, 583 insertions(+), 2 deletions(-)
+ create mode 100644 arch/arm/dts/mt7622-bananapi-bpi-r64-nand.dts
+ create mode 100644 configs/mt7622_bpir64_emmc_defconfig
+ create mode 100644 configs/mt7622_bpir64_sd_defconfig
+ create mode 100644 configs/mt7622_bpir64_snand_defconfig
+
+diff --git a/arch/arm/dts/mt7622-bananapi-bpi-r64-nand.dts b/arch/arm/dts/mt7622-bananapi-bpi-r64-nand.dts
+new file mode 100644
+index 00000000000..afdcb646f69
+--- /dev/null
++++ b/arch/arm/dts/mt7622-bananapi-bpi-r64-nand.dts
+@@ -0,0 +1,290 @@
++// SPDX-License-Identifier: GPL-2.0
++/*
++ * Copyright (c) 2019 MediaTek Inc.
++ * Author: Sam Shih
++ *
++ * BananaPi BPI-R64 - SPI NAND flash variant
++ */
++
++/dts-v1/;
++#include
++#include "mt7622.dtsi"
++#include "mt7622-u-boot.dtsi"
++
++/ {
++ #address-cells = <1>;
++ #size-cells = <1>;
++ model = "mt7622-bpi-r64";
++ compatible = "mediatek,mt7622", "mediatek,mt7622-rfb";
++ chosen {
++ stdout-path = &uart0;
++ tick-timer = &timer0;
++ };
++
++ aliases {
++ spi0 = &snfi;
++ ethernet0 = ð
++ };
++
++ memory@40000000 {
++ device_type = "memory";
++ reg = <0x40000000 0x40000000>;
++ };
++
++ gpio-keys {
++ compatible = "gpio-keys";
++
++ factory-reset {
++ label = "factory-reset";
++ gpios = <&gpio 0 GPIO_ACTIVE_LOW>;
++ linux,code = ;
++ };
++
++ wps {
++ label = "wps";
++ gpios = <&gpio 102 GPIO_ACTIVE_LOW>;
++ linux,code = ;
++ };
++ };
++
++ leds {
++ compatible = "gpio-leds";
++
++ green {
++ label = "bpi-r64:pio:green";
++ gpios = <&gpio 89 GPIO_ACTIVE_HIGH>;
++ default-state = "off";
++ };
++
++ blue {
++ label = "bpi-r64:pio:blue";
++ gpios = <&gpio 85 GPIO_ACTIVE_LOW>;
++ default-state = "off";
++ };
++ };
++
++ reg_1p8v: regulator-1p8v {
++ compatible = "regulator-fixed";
++ regulator-name = "fixed-1.8V";
++ regulator-min-microvolt = <1800000>;
++ regulator-max-microvolt = <1800000>;
++ regulator-boot-on;
++ regulator-always-on;
++ };
++
++ reg_3p3v: regulator-3p3v {
++ compatible = "regulator-fixed";
++ regulator-name = "fixed-3.3V";
++ regulator-min-microvolt = <3300000>;
++ regulator-max-microvolt = <3300000>;
++ regulator-boot-on;
++ regulator-always-on;
++ };
++};
++
++&pcie {
++ pinctrl-names = "default";
++ pinctrl-0 = <&pcie0_pins>, <&pcie1_pins>;
++ status = "okay";
++
++ pcie@0,0 {
++ status = "okay";
++ };
++
++ pcie@1,0 {
++ status = "okay";
++ };
++};
++
++&pinctrl {
++ pcie0_pins: pcie0-pins {
++ mux {
++ function = "pcie";
++ groups = "pcie0_pad_perst",
++ "pcie0_1_waken",
++ "pcie0_1_clkreq";
++ };
++ };
++
++ pcie1_pins: pcie1-pins {
++ mux {
++ function = "pcie";
++ groups = "pcie1_pad_perst",
++ "pcie1_0_waken",
++ "pcie1_0_clkreq";
++ };
++ };
++
++ snfi_pins: snfi-pins {
++ mux {
++ function = "flash";
++ groups = "snfi";
++ };
++ };
++
++ uart0_pins: uart0 {
++ mux {
++ function = "uart";
++ groups = "uart0_0_tx_rx" ;
++ };
++ };
++
++ pwm_pins: pwm1 {
++ mux {
++ function = "pwm";
++ groups = "pwm_ch1_0" ;
++ };
++ };
++
++ watchdog_pins: watchdog-default {
++ mux {
++ function = "watchdog";
++ groups = "watchdog";
++ };
++ };
++
++ mmc0_pins_default: mmc0default {
++ mux {
++ function = "emmc";
++ groups = "emmc";
++ };
++
++ conf-cmd-dat {
++ pins = "NDL0", "NDL1", "NDL2",
++ "NDL3", "NDL4", "NDL5",
++ "NDL6", "NDL7", "NRB";
++ input-enable;
++ bias-pull-up;
++ };
++
++ conf-clk {
++ pins = "NCLE";
++ bias-pull-down;
++ };
++ };
++
++ mmc1_pins_default: mmc1default {
++ mux {
++ function = "sd";
++ groups = "sd_0";
++ };
++
++ conf-cmd-data {
++ pins = "I2S2_OUT", "I2S4_IN", "I2S3_IN",
++ "I2S2_IN","I2S4_OUT";
++ input-enable;
++ drive-strength = <8>;
++ bias-pull-up;
++ };
++
++ conf-clk {
++ pins = "I2S3_OUT";
++ drive-strength = <12>;
++ bias-pull-down;
++ };
++
++ conf-cd {
++ pins = "TXD3";
++ bias-pull-up;
++ };
++ };
++};
++
++&snfi {
++ pinctrl-names = "default";
++ pinctrl-0 = <&snfi_pins>;
++ status = "okay";
++
++ spi-nand@0 {
++ compatible = "spi-nand";
++ reg = <0>;
++ spi-tx-bus-width = <4>;
++ spi-rx-bus-width = <4>;
++
++ partitions {
++ compatible = "fixed-partitions";
++ #address-cells = <1>;
++ #size-cells = <1>;
++
++ partition@0 {
++ label = "bl2";
++ reg = <0x0 0x80000>;
++ };
++
++ partition@80000 {
++ label = "ubi";
++ reg = <0x80000 0x7f80000>;
++ };
++ };
++ };
++};
++
++&uart0 {
++ status = "okay";
++};
++
++&pwm {
++ pinctrl-names = "default";
++ pinctrl-0 = <&pwm_pins>;
++ status = "okay";
++};
++
++&mmc0 {
++ pinctrl-names = "default";
++ pinctrl-0 = <&mmc0_pins_default>;
++ status = "okay";
++ bus-width = <8>;
++ max-frequency = <50000000>;
++ cap-mmc-highspeed;
++ vmmc-supply = <®_3p3v>;
++ vqmmc-supply = <®_3p3v>;
++ non-removable;
++};
++
++&mmc1 {
++ pinctrl-names = "default";
++ pinctrl-0 = <&mmc1_pins_default>;
++ status = "okay";
++ bus-width = <4>;
++ max-frequency = <25000000>;
++ cap-sd-highspeed;
++ r_smpl = <1>;
++ vmmc-supply = <®_3p3v>;
++ vqmmc-supply = <®_3p3v>;
++};
++
++&watchdog {
++ pinctrl-names = "default";
++ pinctrl-0 = <&watchdog_pins>;
++ status = "okay";
++};
++
++ð {
++ status = "okay";
++ mediatek,gmac-id = <0>;
++ phy-mode = "2500base-x";
++ mediatek,switch = "mt7531";
++ reset-gpios = <&gpio 54 GPIO_ACTIVE_HIGH>;
++
++ fixed-link {
++ speed = <2500>;
++ full-duplex;
++ };
++};
++
++&gpio {
++ /*gpio 90 for setting mode to sata*/
++ asm_sel {
++ gpio-hog;
++ gpios = <90 GPIO_ACTIVE_HIGH>;
++ output-low;
++ };
++};
++
++&ssusb {
++ status = "okay";
++};
++
++&u3phy {
++ status = "okay";
++};
+diff --git a/arch/arm/dts/mt7622-bananapi-bpi-r64.dts b/arch/arm/dts/mt7622-bananapi-bpi-r64.dts
+index 717baf26d3f..f25257be63d 100644
+--- a/arch/arm/dts/mt7622-bananapi-bpi-r64.dts
++++ b/arch/arm/dts/mt7622-bananapi-bpi-r64.dts
+@@ -5,6 +5,7 @@
+ */
+
+ /dts-v1/;
++#include
+ #include "mt7622.dtsi"
+ #include "mt7622-u-boot.dtsi"
+
+@@ -20,6 +21,7 @@
+
+ aliases {
+ spi0 = &snfi;
++ ethernet0 = ð
+ };
+
+ memory@40000000 {
+@@ -27,6 +29,38 @@
+ reg = <0x40000000 0x40000000>;
+ };
+
++ gpio-keys {
++ compatible = "gpio-keys";
++
++ factory-reset {
++ label = "factory-reset";
++ gpios = <&gpio 0 GPIO_ACTIVE_LOW>;
++ linux,code = ;
++ };
++
++ wps {
++ label = "wps";
++ gpios = <&gpio 102 GPIO_ACTIVE_LOW>;
++ linux,code = ;
++ };
++ };
++
++ leds {
++ compatible = "gpio-leds";
++
++ green {
++ label = "bpi-r64:pio:green";
++ gpios = <&gpio 89 GPIO_ACTIVE_HIGH>;
++ default-state = "off";
++ };
++
++ blue {
++ label = "bpi-r64:pio:blue";
++ gpios = <&gpio 85 GPIO_ACTIVE_LOW>;
++ default-state = "off";
++ };
++ };
++
+ reg_1p8v: regulator-1p8v {
+ compatible = "regulator-fixed";
+ regulator-name = "fixed-1.8V";
+@@ -197,7 +231,7 @@
+ status = "okay";
+ bus-width = <8>;
+ max-frequency = <50000000>;
+- cap-sd-highspeed;
++ cap-mmc-highspeed;
+ vmmc-supply = <®_3p3v>;
+ vqmmc-supply = <®_3p3v>;
+ non-removable;
+@@ -208,7 +242,7 @@
+ pinctrl-0 = <&mmc1_pins_default>;
+ status = "okay";
+ bus-width = <4>;
+- max-frequency = <50000000>;
++ max-frequency = <25000000>;
+ cap-sd-highspeed;
+ r_smpl = <1>;
+ vmmc-supply = <®_3p3v>;
+diff --git a/board/mediatek/mt7622/MAINTAINERS b/board/mediatek/mt7622/MAINTAINERS
+index a3e0e75ca07..a7da7948a65 100644
+--- a/board/mediatek/mt7622/MAINTAINERS
++++ b/board/mediatek/mt7622/MAINTAINERS
+@@ -4,3 +4,8 @@ S: Maintained
+ F: board/mediatek/mt7622
+ F: include/configs/mt7622.h
+ F: configs/mt7622_rfb_defconfig
++F: configs/mt7622_bpir64_emmc_defconfig
++F: configs/mt7622_bpir64_sd_defconfig
++F: configs/mt7622_bpir64_snand_defconfig
++F: arch/arm/dts/mt7622-bananapi-bpi-r64.dts
++F: arch/arm/dts/mt7622-bananapi-bpi-r64-nand.dts
+diff --git a/configs/mt7622_bpir64_emmc_defconfig b/configs/mt7622_bpir64_emmc_defconfig
+new file mode 100644
+index 00000000000..9af7b280c93
+--- /dev/null
++++ b/configs/mt7622_bpir64_emmc_defconfig
+@@ -0,0 +1,82 @@
++CONFIG_ARM=y
++CONFIG_SYS_HAS_NONCACHED_MEMORY=y
++CONFIG_POSITION_INDEPENDENT=y
++CONFIG_ARCH_MEDIATEK=y
++CONFIG_TARGET_MT7622=y
++CONFIG_TEXT_BASE=0x41e00000
++CONFIG_SYS_MALLOC_F_LEN=0x4000
++CONFIG_NR_DRAM_BANKS=1
++CONFIG_ENV_SIZE=0x80000
++CONFIG_ENV_OFFSET=0x400000
++CONFIG_DEFAULT_DEVICE_TREE="mt7622-bananapi-bpi-r64"
++CONFIG_SYS_LOAD_ADDR=0x40080000
++CONFIG_DEBUG_UART_BASE=0x11002000
++CONFIG_DEBUG_UART_CLOCK=25000000
++CONFIG_PCI=y
++CONFIG_DEBUG_UART=y
++CONFIG_FIT=y
++# CONFIG_EFI_LOADER is not set
++# CONFIG_AUTOBOOT is not set
++CONFIG_DEFAULT_FDT_FILE="mt7622-bananapi-bpi-r64"
++CONFIG_SYS_CBSIZE=512
++CONFIG_SYS_PBSIZE=1049
++CONFIG_LOGLEVEL=7
++CONFIG_LOG=y
++CONFIG_SYS_PROMPT="BPI-R64> "
++# CONFIG_BOOTM_NETBSD is not set
++# CONFIG_BOOTM_PLAN9 is not set
++# CONFIG_BOOTM_RTEMS is not set
++# CONFIG_BOOTM_VXWORKS is not set
++# CONFIG_CMD_ELF is not set
++# CONFIG_CMD_UNLZ4 is not set
++# CONFIG_CMD_UNZIP is not set
++CONFIG_CMD_GPIO=y
++CONFIG_CMD_GPT=y
++CONFIG_CMD_GPT_RENAME=y
++CONFIG_CMD_LSBLK=y
++CONFIG_CMD_MMC=y
++CONFIG_CMD_PART=y
++CONFIG_CMD_READ=y
++CONFIG_CMD_PCI=y
++CONFIG_CMD_USB=y
++CONFIG_CMD_PING=y
++CONFIG_CMD_SMC=y
++CONFIG_CMD_FAT=y
++CONFIG_CMD_FS_GENERIC=y
++CONFIG_PARTITION_TYPE_GUID=y
++CONFIG_ENV_OVERWRITE=y
++CONFIG_ENV_IS_IN_MMC=y
++CONFIG_ENV_VARS_UBOOT_RUNTIME_CONFIG=y
++CONFIG_NET_RANDOM_ETHADDR=y
++CONFIG_REGMAP=y
++CONFIG_SYSCON=y
++CONFIG_BUTTON=y
++CONFIG_BUTTON_GPIO=y
++CONFIG_CLK=y
++CONFIG_GPIO_HOG=y
++CONFIG_LED=y
++CONFIG_LED_GPIO=y
++CONFIG_SUPPORT_EMMC_BOOT=y
++CONFIG_MMC_HS200_SUPPORT=y
++CONFIG_MMC_MTK=y
++CONFIG_PHY_FIXED=y
++CONFIG_MEDIATEK_ETH=y
++CONFIG_PCIE_MEDIATEK=y
++CONFIG_PHY=y
++CONFIG_PHY_MTK_TPHY=y
++CONFIG_PINCTRL=y
++CONFIG_PINCONF=y
++CONFIG_PINCTRL_MT7622=y
++CONFIG_POWER_DOMAIN=y
++CONFIG_MTK_POWER_DOMAIN=y
++CONFIG_DM_REGULATOR=y
++CONFIG_DM_REGULATOR_FIXED=y
++CONFIG_RAM=y
++CONFIG_DM_SERIAL=y
++CONFIG_MTK_SERIAL=y
++CONFIG_USB=y
++CONFIG_USB_XHCI_HCD=y
++CONFIG_USB_XHCI_MTK=y
++CONFIG_USB_STORAGE=y
++CONFIG_FAT_WRITE=y
++CONFIG_HEXDUMP=y
+diff --git a/configs/mt7622_bpir64_sd_defconfig b/configs/mt7622_bpir64_sd_defconfig
+new file mode 100644
+index 00000000000..5e9340a09a6
+--- /dev/null
++++ b/configs/mt7622_bpir64_sd_defconfig
+@@ -0,0 +1,82 @@
++CONFIG_ARM=y
++CONFIG_SYS_HAS_NONCACHED_MEMORY=y
++CONFIG_POSITION_INDEPENDENT=y
++CONFIG_ARCH_MEDIATEK=y
++CONFIG_TARGET_MT7622=y
++CONFIG_TEXT_BASE=0x41e00000
++CONFIG_SYS_MALLOC_F_LEN=0x4000
++CONFIG_NR_DRAM_BANKS=1
++CONFIG_ENV_SIZE=0x80000
++CONFIG_ENV_OFFSET=0x400000
++CONFIG_DEFAULT_DEVICE_TREE="mt7622-bananapi-bpi-r64"
++CONFIG_SYS_LOAD_ADDR=0x40080000
++CONFIG_DEBUG_UART_BASE=0x11002000
++CONFIG_DEBUG_UART_CLOCK=25000000
++CONFIG_PCI=y
++CONFIG_DEBUG_UART=y
++CONFIG_FIT=y
++# CONFIG_EFI_LOADER is not set
++# CONFIG_AUTOBOOT is not set
++CONFIG_DEFAULT_FDT_FILE="mt7622-bananapi-bpi-r64"
++CONFIG_SYS_CBSIZE=512
++CONFIG_SYS_PBSIZE=1049
++CONFIG_LOGLEVEL=7
++CONFIG_LOG=y
++CONFIG_SYS_PROMPT="BPI-R64> "
++# CONFIG_BOOTM_NETBSD is not set
++# CONFIG_BOOTM_PLAN9 is not set
++# CONFIG_BOOTM_RTEMS is not set
++# CONFIG_BOOTM_VXWORKS is not set
++# CONFIG_CMD_ELF is not set
++# CONFIG_CMD_UNLZ4 is not set
++# CONFIG_CMD_UNZIP is not set
++CONFIG_CMD_GPIO=y
++CONFIG_CMD_GPT=y
++CONFIG_CMD_GPT_RENAME=y
++CONFIG_CMD_LSBLK=y
++CONFIG_CMD_MMC=y
++CONFIG_CMD_PART=y
++CONFIG_CMD_READ=y
++CONFIG_CMD_PCI=y
++CONFIG_CMD_USB=y
++CONFIG_CMD_PING=y
++CONFIG_CMD_SMC=y
++CONFIG_CMD_FAT=y
++CONFIG_CMD_FS_GENERIC=y
++CONFIG_PARTITION_TYPE_GUID=y
++CONFIG_ENV_OVERWRITE=y
++CONFIG_ENV_IS_IN_MMC=y
++CONFIG_SYS_MMC_ENV_DEV=1
++CONFIG_ENV_VARS_UBOOT_RUNTIME_CONFIG=y
++CONFIG_NET_RANDOM_ETHADDR=y
++CONFIG_REGMAP=y
++CONFIG_SYSCON=y
++CONFIG_BUTTON=y
++CONFIG_BUTTON_GPIO=y
++CONFIG_CLK=y
++CONFIG_GPIO_HOG=y
++CONFIG_LED=y
++CONFIG_LED_GPIO=y
++CONFIG_MMC_HS200_SUPPORT=y
++CONFIG_MMC_MTK=y
++CONFIG_PHY_FIXED=y
++CONFIG_MEDIATEK_ETH=y
++CONFIG_PCIE_MEDIATEK=y
++CONFIG_PHY=y
++CONFIG_PHY_MTK_TPHY=y
++CONFIG_PINCTRL=y
++CONFIG_PINCONF=y
++CONFIG_PINCTRL_MT7622=y
++CONFIG_POWER_DOMAIN=y
++CONFIG_MTK_POWER_DOMAIN=y
++CONFIG_DM_REGULATOR=y
++CONFIG_DM_REGULATOR_FIXED=y
++CONFIG_RAM=y
++CONFIG_DM_SERIAL=y
++CONFIG_MTK_SERIAL=y
++CONFIG_USB=y
++CONFIG_USB_XHCI_HCD=y
++CONFIG_USB_XHCI_MTK=y
++CONFIG_USB_STORAGE=y
++CONFIG_FAT_WRITE=y
++CONFIG_HEXDUMP=y
+diff --git a/configs/mt7622_bpir64_snand_defconfig b/configs/mt7622_bpir64_snand_defconfig
+new file mode 100644
+index 00000000000..9be13d26fd9
+--- /dev/null
++++ b/configs/mt7622_bpir64_snand_defconfig
+@@ -0,0 +1,88 @@
++CONFIG_ARM=y
++CONFIG_SYS_HAS_NONCACHED_MEMORY=y
++CONFIG_POSITION_INDEPENDENT=y
++CONFIG_ARCH_MEDIATEK=y
++CONFIG_TARGET_MT7622=y
++CONFIG_TEXT_BASE=0x41e00000
++CONFIG_SYS_MALLOC_F_LEN=0x4000
++CONFIG_NR_DRAM_BANKS=1
++CONFIG_DEFAULT_DEVICE_TREE="mt7622-bananapi-bpi-r64-nand"
++CONFIG_SYS_LOAD_ADDR=0x40080000
++CONFIG_DEBUG_UART_BASE=0x11002000
++CONFIG_DEBUG_UART_CLOCK=25000000
++CONFIG_PCI=y
++CONFIG_DEBUG_UART=y
++CONFIG_FIT=y
++# CONFIG_EFI_LOADER is not set
++# CONFIG_AUTOBOOT is not set
++CONFIG_DEFAULT_FDT_FILE="mt7622-bananapi-bpi-r64-nand"
++CONFIG_SYS_CBSIZE=512
++CONFIG_SYS_PBSIZE=1049
++CONFIG_LOGLEVEL=7
++CONFIG_LOG=y
++CONFIG_SYS_PROMPT="BPI-R64> "
++# CONFIG_BOOTM_NETBSD is not set
++# CONFIG_BOOTM_PLAN9 is not set
++# CONFIG_BOOTM_RTEMS is not set
++# CONFIG_BOOTM_VXWORKS is not set
++# CONFIG_CMD_ELF is not set
++# CONFIG_CMD_UNLZ4 is not set
++# CONFIG_CMD_UNZIP is not set
++CONFIG_CMD_GPIO=y
++CONFIG_CMD_MMC=y
++CONFIG_CMD_MTD=y
++CONFIG_CMD_PART=y
++CONFIG_CMD_READ=y
++CONFIG_CMD_PCI=y
++CONFIG_CMD_USB=y
++CONFIG_CMD_PING=y
++CONFIG_CMD_SMC=y
++CONFIG_CMD_FAT=y
++CONFIG_CMD_FS_GENERIC=y
++CONFIG_CMD_UBI=y
++CONFIG_PARTITION_TYPE_GUID=y
++CONFIG_ENV_OVERWRITE=y
++CONFIG_ENV_IS_IN_UBI=y
++CONFIG_ENV_REDUNDANT=y
++CONFIG_ENV_UBI_PART="ubi"
++CONFIG_ENV_UBI_VOLUME="ubootenv"
++CONFIG_ENV_UBI_VOLUME_REDUND="ubootenv2"
++CONFIG_ENV_VARS_UBOOT_RUNTIME_CONFIG=y
++CONFIG_NET_RANDOM_ETHADDR=y
++CONFIG_REGMAP=y
++CONFIG_SYSCON=y
++CONFIG_BUTTON=y
++CONFIG_BUTTON_GPIO=y
++CONFIG_CLK=y
++CONFIG_GPIO_HOG=y
++CONFIG_LED=y
++CONFIG_LED_GPIO=y
++CONFIG_MMC_HS200_SUPPORT=y
++CONFIG_MMC_MTK=y
++CONFIG_MTD=y
++CONFIG_DM_MTD=y
++CONFIG_MTD_SPI_NAND=y
++CONFIG_PHY_FIXED=y
++CONFIG_MEDIATEK_ETH=y
++CONFIG_PCIE_MEDIATEK=y
++CONFIG_PHY=y
++CONFIG_PHY_MTK_TPHY=y
++CONFIG_PINCTRL=y
++CONFIG_PINCONF=y
++CONFIG_PINCTRL_MT7622=y
++CONFIG_POWER_DOMAIN=y
++CONFIG_MTK_POWER_DOMAIN=y
++CONFIG_DM_REGULATOR=y
++CONFIG_DM_REGULATOR_FIXED=y
++CONFIG_RAM=y
++CONFIG_DM_SERIAL=y
++CONFIG_MTK_SERIAL=y
++CONFIG_SPI=y
++CONFIG_DM_SPI=y
++CONFIG_MTK_SNFI_SPI=y
++CONFIG_USB=y
++CONFIG_USB_XHCI_HCD=y
++CONFIG_USB_XHCI_MTK=y
++CONFIG_USB_STORAGE=y
++CONFIG_FAT_WRITE=y
++CONFIG_HEXDUMP=y
+--
+2.43.0
+
diff --git a/utils/mkimage.sh b/utils/mkimage.sh
index 41698182b..882d34bab 100755
--- a/utils/mkimage.sh
+++ b/utils/mkimage.sh
@@ -186,6 +186,13 @@ get_bootloader_name()
echo "bpi_r3_sd_boot"
fi
;;
+ bananapi-bpi-r64)
+ if [ "$target" = "emmc" ]; then
+ echo "bpi_r64_emmc_boot"
+ else
+ echo "bpi_r64_sd_boot"
+ fi
+ ;;
friendlyarm-nanopi-r2s)
echo "nanopi_r2s_boot"
;;