[BPI-R4] How to get an openwrt image to eMMC?

Hello! I have been building my own version of openwrt for a while and now I have been using that with the SD image flashed to… an SD.

Now, when I build I get all of these output files:

mt7981-ram-ddr3-bl2.bin
mt7981-ram-ddr4-bl2.bin
mt7986-ram-ddr3-bl2.bin
mt7986-ram-ddr4-bl2.bin
mt7988-ram-comb-bl2.bin
openwrt-mediatek-filogic-bananapi_bpi-r4-emmc-bl31-uboot.fip
openwrt-mediatek-filogic-bananapi_bpi-r4-emmc-preloader.bin
openwrt-mediatek-filogic-bananapi_bpi-r4-initramfs-recovery.itb
openwrt-mediatek-filogic-bananapi_bpi-r4.manifest
openwrt-mediatek-filogic-bananapi_bpi-r4-sdcard.img.gz
openwrt-mediatek-filogic-bananapi_bpi-r4-snand-bl31-uboot.fip
openwrt-mediatek-filogic-bananapi_bpi-r4-snand-preloader.bin
openwrt-mediatek-filogic-bananapi_bpi-r4-squashfs-sysupgrade.itb

How can I install the same build first on the NAND and then on the eMMC?

Thank you!

Afair it is designed to boot the sdcard one first and then install to nand from it,then boot this and install emmc

Yeah, I tried to use the process in Getting Started BPI-R4 | BananaPi Docs assuming is the same but then I get to:

root@OpenWrt:/mnt# mtd erase /dev/mtd0
Could not open mtd device: /dev/mtd0
Could not open mtd device: /dev/mtd0
root@OpenWrt:/mnt# cat /proc/mtd
dev:    size   erasesize  name
mtd0: 00200000 00020000 "bl2"
mtd1: 07e00000 00020000 "ubi"

Any clue on what am I missing?

Do not use the bpi way here…mainline openwrt is installed using uboot menu

But if I want to boot something else in NAND and install an OpenWRT directly to emmc anyone know which is the procedure? I’m having trouble with the bl31-uboot as well. I tried with mmcblk0p4 and mmcblk0p3 without success.

dd if=openwrt-mediatek-filogic-bananapi_bpi-r4-emmc-bl31-uboot.fip of=/dev/mmcblk0p4

I’m getting:

NOTICE:  BL2: v2.13.0(release):OpenWrt v2025.07.11~78a0dfd9-1 (mt7988-emmc-comb)
NOTICE:  BL2: Built : 23:20:01, Feb  4 2026
NOTICE:  WDT: Cold boot
NOTICE:  WDT: disabled
NOTICE:  CPU: MT7988
NOTICE:  EMI: Using DDR unknown settings
NOTICE:  EMI: Detected DRAM size: 4096 MB
NOTICE:  EMI: complex R/W mem test passed
NOTICE:  LVTS: Enable thermal HW reset
NOTICE:  Located partition 'fip' at 0x680000, size 0x400000
ERROR:   io_dev_init failed for FIP image id 0 (-2)
ERROR:   Image id 3 open failed with -2
ERROR:   BL2: Failed to load image id 3 (-2)

thanks!

all these images are loaded in the sdcard - using the uboot menu you can choose an option to copy the files to the nand, and then from the nand to the emmc

if you want to change the default images names you need to change the uboot env variables or otherwise look at the package uboot-mediatek there will be patches (450-add-bpi-r4.patch) there that set the env variables for each device

Openwrt uses fip (uboot+bl3) in ubi…so you have to create an ubifs,add a partition names “fip” and then flash the fip image there

Thanks, but emmc handles the translation. I don’t think ubi is used here. ubi works well for flash memories like NAND. Regarding the boot menu that’s what I was trying to avoid. Not having to flash NAND again, and directly flash a new verison to test to EMMC. Anyways I was able to make it work with something like this:

dd if=openwrt-mediatek-filogic-bananapi_bpi-r4-emmc-gpt.bin of=/dev/mmcblk0 bs=512 count=34 conv=fsync
blockdev --rereadpt /dev/mmcblk0
echo 0 > /sys/block/mmcblk0boot0/force_ro
dd if=/dev/zero of=/dev/mmcblk0boot0 bs=512 count=8192 conv=fsync
dd if=/dev/zero of=/dev/mmcblk0 bs=512 seek=13312 count=8192 conv=fsync
dd if=openwrt-mediatek-filogic-bananapi_bpi-r4-emmc-preloader.bin of=/dev/mmcblk0boot0 conv=fsync
dd if=openwrt-mediatek-filogic-bananapi_bpi-r4-emmc-bl31-uboot.fip of=/dev/mmcblk0p3 conv=fsync
dd if=openwrt-mediatek-filogic-bananapi_bpi-r4-initramfs-recovery.itb of=/dev/mmcblk0p4 conv=fsync
dd if=openwrt-mediatek-filogic-bananapi_bpi-r4-squashfs-sysupgrade.itb of=/dev/mmcblk0p5 conv=fsync

I’ll be updating the bpi-r4 openwrt installation page with this.

Sorry,misunderstood…thought you wanted nand installation…yes for emmc it should work like you posted. Did not know that gpt binary is also available from openwrt imagebuilder to be flashed.

BPI-R4 8GB: physical RAM confirmed, and how to actually get eMMC to boot with all 8GB

TL;DR

  • If your “8GB” BPI-R4 shows only 4GB via the stock/default OpenWrt bootloader, that’s not a sign you got a mislabeled 4GB board. It’s a known limitation: the default BL2 doesn’t have DDR4-4BG training enabled.
  • Getting the SD card to report 8GB is one image-selection choice away (see below).
  • Getting the eMMC to boot natively with 8GB is a separate, undocumented multi-step process, because eMMC ships from the factory with its boot partition disabled. Full working procedure below.
  • I’ve also submitted a small doc/UX patch upstream so the boot menu itself hints at the correct order: uboot-mediatek: bpi-r4: clarify eMMC install is a two-step process by dexter939 · Pull Request #24912 · openwrt/openwrt · GitHub

Background

Board: Bananapi BPI-R4, purchased as the 8GB RAM variant. Wanted to verify the RAM was genuinely 8GB (some 8GB-labeled units in the wild turn out to be relabeled 4GB boards), and get OpenWrt properly using all of it from eMMC.

Step 1 — Confirm the RAM is really 8GB (independent of what boots)

Connect UART (115200 8N1) and watch the BL2/EMI lines. What matters is:

NOTICE:  EMI: DDR4 4BG mode
NOTICE:  DRAM: 8192MB

On my unit, the stock eMMC-installed bootloader (upstream OpenWrt default, non-“4bg” BL2 variant) only ever showed:

NOTICE:  EMI: Using DDR unknown settings
NOTICE:  EMI: Detected DRAM size: 4096 MB

This had me worried the board was actually 4GB. It isn’t — the default BL2 that ships in most OpenWrt builds for this target simply isn’t compiled with DDR4_4BG_MODE, so it never even attempts to train/detect the extra half of the DRAM package. I confirmed the real physical capacity independently four separate times, each with a different BL2/environment:

  1. Official OpenWrt snapshot bananapi_bpi-r4-sdcard_8g.img.gz booted from SD (mt7988-sdmmc-comb-4bg) → 8192MB
  2. The board’s original factory/vendor BL2 sitting untouched in SPI-NAND (v2.11.0, no OpenWrt version string, predates any of my flashing) → also reports 8192MB when it happens to run
  3. The mt7988-emmc-comb-4bg BL2 once properly installed to eMMC (see below) → 8192MB
  4. free -h from Linux booted natively off eMMC → MemTotal: 8137076 kB (~7.76 GiB usable, normal after reserved regions)

If your board shows only 4096MB no matter what, and you’ve confirmed via a -8g/4bg bootloader variant specifically, then it’s genuinely a 4GB board or something is actually wrong. If you’ve only ever tried the default non-4bg bootloader, that result is meaningless — you haven’t actually tested for 8GB yet.

Step 2 — SD card: trivial

Just download and flash the official snapshot image:

openwrt-mediatek-filogic-bananapi_bpi-r4-sdcard_8g.img.gz

from https://downloads.openwrt.org/snapshots/targets/mediatek/filogic/. Verify against sha256sums in the same directory, write raw to the SD card (Rufus/dd/Etcher). That’s it — boots straight to 8GB with the SW3 switch on SD.

Step 3 — eMMC: this is the part nobody documents

This is where it gets interesting. Short version: you cannot write to the eMMC while booted from SD. The SD card slot and the eMMC chip share the exact same physical MMC host controller on the SoC (11230000.mmc), multiplexed by the SW3 switch. With the switch on SD, dmesg shows exactly one mmc0 device and it’s the SD card — the eMMC is electrically disconnected, full stop, not a driver/software limitation.

SW3 switch reference (from the silkscreen on my unit)

Storage A B
NAND 0 (up) 1 (down)
eMMC 1 (down) 0 (up)
SD 1 (down) 1 (down)

Why NAND is unavoidable as a middle step

SPI-NAND sits on a completely separate SPI bus, so it’s reachable from U-Boot/Linux regardless of the SW3 position. It’s used purely as a temporary “bridge” to carry the eMMC installer payload across a switch position change that software can’t perform on its own (it’s a physical DIP switch).

The actual procedure

  1. Switch = SD. Boot. Stop autoboot, use the bootmenu → “Install bootloader, recovery and production to NAND.” This formats the NAND UBI and, as a side effect, also copies an 8MB emmc_install payload (read from the SD’s own “install” GPT partition) into a NAND UBI volume of the same name.
  2. Switch = NAND. Reboot. You’ll now get a new bootmenu entry that didn’t exist before: “Install bootloader, recovery and production to eMMC.” Select it.Under the hood this runs (from the board’s own U-Boot env, defenvs/bananapi_bpi-r4_snand_env in the u-boot-mediatek OpenWrt package):
emmc_init=mmc dev 0 && mmc bootbus 0 0 0 0 && run emmc_init_bl && run emmc_init_openwrt ; env default bootcmd ; saveenv ; saveenv
emmc_init_bl=run ubi_read_emmc_install && setenv fileaddr $loadaddr && run emmc_write_bl2 && setexpr fileaddr $loadaddr + 0x100000 && run emmc_write_fip && setexpr fileaddr $loadaddr + 0x500000 && run emmc_write_hdr
emmc_write_bl2=mmc partconf 0 1 1 1 && mmc erase 0x0 0x400 && mmc write $fileaddr 0x0 0x400 ; mmc partconf 0 1 1 0
emmc_write_fip=mmc erase 0x3400 0x2000 && mmc write $fileaddr 0x3400 0x2000 && mmc erase 0x2000 0x800
emmc_write_hdr=mmc erase 0x0 0x40 && mmc write $fileaddr 0x0 0x40

Critically, mmc partconf 0 1 1 1 both enables the eMMC boot partition (BOOT_PARTITION_ENABLE, EXT_CSD byte 179 — factory default is 0x00, i.e. disabled!) and temporarily redirects access to it for the BL2 write, before switching access back to the user area for FIP/GPT/recovery/production. 3. Switch = eMMC. Reboot. You should now see:

BL2: v2.14.0(release):OpenWrt ... (mt7988-emmc-comb-4bg)
EMI: DDR4 4BG mode
DRAM: 8192MB
...
Model: Bananapi BPI-R4
DRAM:  8 GiB

And Linux itself (free -h) confirms the full 8GB.

If you get stuck at “System halt!” repeating forever with switch=eMMC

That’s the board’s Boot ROM failing to find a valid signature on the eMMC boot partition. Two likely causes, in order of likelihood:

  • You haven’t done step 1+2 yet (eMMC genuinely blank, nothing to boot).
  • PARTITION_CONFIG isn’t enabled. You can check/fix this manually from Linux (booted from NAND, where eMMC is visible as /dev/mmcblk0) with mmc-utils (apk add mmc-utils on newer apk-based snapshots, or opkg install mmc-utils):
mmc extcsd read /dev/mmcblk0 | grep -A2 PARTITION_CONFIG
mmc bootpart enable 1 1 /dev/mmcblk0

In practice you shouldn’t need to do this by hand — the official “Install to eMMC” menu option does it for you as shown above. I only needed it once, early on, while I was still reverse-engineering the problem before finding the proper menu entry.

A note on flaky serial connections

If your UART capture starts producing pure noise (random bytes, not garbage-but-readable text) partway through this process, don’t waste time debugging U-Boot — it’s almost always a physical connection issue (I burned through a CH340-based adapter that developed exactly this problem after repeated reconnects; swapping to an FTDI-based adapter fixed it instantly). Confirm with mode COM3 on Windows or by reading the port directly with a minimal script, independent of whatever terminal program you’re using, before assuming it’s a software/board problem.

Menu clarity patch

None of the above sequencing is hinted at anywhere in the boot menu itself — “Install to NAND” doesn’t say it’s also a prerequisite for eMMC, and the “Install to eMMC” option is invisible until you’ve already done that first step, with no explanation why. I’ve submitted a small patch upstream that just renames the two menu entries to state their place in the sequence:

Install bootloader, recovery and production to NAND (step 1/2, required before eMMC install).
Install bootloader, recovery and production to eMMC (step 2/2, run Install to NAND from SD first).

PR: uboot-mediatek: bpi-r4: clarify eMMC install is a two-step process by dexter939 · Pull Request #24912 · openwrt/openwrt · GitHub

Hope this saves someone else the couple of days I spent on it.

btw - you can use this part A and C in readme😉