GL.iNet GL-BE9300 (Flint 3)

No official support now

Use the factory image, not the sysupgrade image, when coming from stock. GL's platform_check_image only accepts a QSDK FIT containing hlos and rootfs. The OpenWrt factory image is built in that format; the normal sysupgrade image is not and must never be forced from stock.

The GL.iNet Flint 3 (GL-BE9300) is a Wi-Fi 7 router based on the Qualcomm IPQ5332, with a Realtek RTL8372N switch providing four 2.5 GbE LAN ports and an RTL8221B 2.5 GbE WAN port, plus tri-band Wi-Fi (IPQ5332 for 2.4 GHz and a dual-mac QCN9274 for 5 GHz and 6 GHz).

gl-be9300

Support Forum: GL.iNet Flint 3 exploration

Build the custom firmware first: https://github.com/perceival/openwrt-flint3

Use the factory image, not the sysupgrade image, when coming from stock. GL's platform_check_image only accepts a QSDK FIT containing hlos and rootfs. The OpenWrt factory image is built in that format; the normal sysupgrade image is not and must never be forced from stock.

Do this first, from the running stock firmware. The ART partition holds this unit's radio calibration, MAC addresses and factory country code, and is not recoverable from anywhere else.

ssh root@192.168.8.1 'dd if=/dev/mmcblk0 bs=1M' > flint3-emmc-full.img

Windows users: Better not use PowerShell for that (cmd.exe or WSL will still do).

Copy the factory image to the router and force the upgrade:

scp openwrt-*-glinet_gl-be9300-squashfs-factory.bin root@192.168.8.1:/tmp/factory.bin
ssh root@192.168.8.1 'sysupgrade -F -n /tmp/factory.bin'

-F is required: stock's image check fails because our factory image carries no bootloader payloads, and it says so before continuing:

upgrade: Supported devices: glinet,gl-be9300 gl.inet,gl-be9300
Warning: optional section "sb11" missing from "/tmp/factory.bin". Continue...
Warning: optional section "u-boot" missing from "/tmp/factory.bin". Continue...
Warning: optional section "tz" missing from "/tmp/factory.bin". Continue...
Image check failed but --force given - will update anyway!

Those warnings are expected — the missing sections are U-Boot, TZ and DDR payloads which OpenWrt deliberately does not replace.

-n is also recommended: it discards the stock configuration rather than trying to carry GL's UCI files into OpenWrt. The router then boots whatever configuration is baked into the image.

The SSH session ends when the device reboots. Note that the vendor firmware has no setsid, so run the command in the foreground.

Only needed if you have no factory image — for example when installing a build that predates it. This replicates what OpenWrt's emmc_upgrade_tar() does: invalidate the kernel, write rootfs, write kernel, then verify.

ssh root@192.168.8.1 'sh -s' <<'EOF'
set -e
TAR=/tmp/su.bin; KERN=/dev/mmcblk0p12; ROOT=/dev/mmcblk0p13
DIR=$(tar tf "$TAR" | grep -m1 '^sysupgrade-.*/$'); DIR=${DIR%/}
dd if=/dev/zero of="$KERN" bs=512 count=8; sync
B=$(tar -xOf "$TAR" "$DIR/root" | dd of="$ROOT" bs=512 2>&1 | grep "records out" | cut -d' ' -f1); sync
tar -xOf "$TAR" "$DIR/kernel" | dd of="$KERN" bs=512; sync
dd if=/dev/zero of="$ROOT" bs=512 seek=$(( (${B%%+*} + 127) & ~127 )) count=8; sync
dd if="$KERN" bs=4 count=1 | hexdump -e '4/1 "%02x"'; echo " <- want d00dfeed"
dd if="$ROOT" bs=4 count=1 | hexdump -e '4/1 "%02x"'; echo " <- want 68737173 (hsqs)"
EOF

Reboot only if both magic values are correct. The device then comes up as a default OpenWrt at 192.168.1.1.

Run both commands against the router's current OpenWrt address — it is still running OpenWrt at this point. Substitute your own address for 192.168.1.1 below.

# on your PC: copy a stock GL.iNet image to the router
scp be9300-*.bin root@192.168.1.1:/tmp/stock.bin

# optional but worth doing: confirm the router can parse it before writing
ssh root@192.168.1.1 'dumpimage -l /tmp/stock.bin'
#   expect: FIT description: Flashing factory image
#           Image 0 (script) / 1 (wifi_fw) / 2 (hlos) / 3 (rootfs)

ssh root@192.168.1.1 'sysupgrade -n /tmp/stock.bin'

Stock images are available from https://dl.gl-inet.com/router/be9300/

-n is required — the stock configuration cannot be carried across.

OpenWrt reads the FIT metadata and writes wifi_fw, hlos and rootfs to 0:WIFIFW, 0:HLOS and the rootfs partition, kernel last so an interrupted restore cannot boot a partial image. This needs dumpimage in the OpenWrt image; check with which dumpimage first.

The router's address changes. After rebooting into stock it is a router again at 192.168.8.1, reachable through its LAN ports; the WAN port becomes a DHCP client. SSH is disabled on stock until you complete the setup wizard in the web UI and set an admin password — that password is also root's SSH password.

httpd 192.168.1.99 plus a browser or curl upload prints

HTTP ugrade is done! Rebooting...

but does not write flash when given a non-vendor image: afterwards 0:HLOS still contains the previous FIT and rootfs still begins with hsqs. 0:HLOS is only 7 MiB (LBA 0xa622..0xde21), so a ~22 MB initramfs FIT could not fit there in any case.

What it does do is leave the uploaded image at 0x50000000 in DRAM, and that survives the warm reset. So it is a convenient way to RAM-boot an image for testing without touching the eMMC:

# upload via httpd, let it "reboot", interrupt autoboot with gl, then:
md.l 0x50000000 2      # expect edfe0dd0 followed by the FIT totalsize
bootm 0x50000000       # = the uploaded file size

Because the eMMC is untouched, the previous installation remains as a fallback. Check the Linux version line in the boot banner to confirm what is actually running — the “done! Rebooting” message does not mean anything was installed.

tftpboot is not usable on this U-Boot for an unrelated reason: it always targets UDP port 69 and tftpdstp is unsupported, so the TFTP server has to listen on the privileged port.

From OpenWrt, a stock GL.iNet image can be written back directly:

scp be9300-*.bin root@192.168.8.1:/tmp/stock.bin     # adjust to your LAN address
ssh root@<router> 'sysupgrade -n /tmp/stock.bin'

OpenWrt recognises the stock image's FIT metadata and extracts wifi_fw, hlos and rootfs into 0:WIFIFW, 0:HLOS and the rootfs partition, writing the kernel last so an interrupted restore cannot boot a partial image. -n is required.

This needs the dumpimage utility present in the OpenWrt image — it is what unpacks the FIT. Verify with which dumpimage before starting.

After restoring stock, the router comes back as a router: LAN 192.168.8.1 with its own DHCP server, and only the WAN port acting as a client. If it is cabled into an existing network, unplug its LAN ports first or it will hand out 192.168.8.x leases to your own machines.

  • The FIT configuration node must be named config-1 (DEVICE_DTS_CONFIG := config-1). Stock U-Boot selects a FIT config by name from a built-in board table that has no AP-MI01.6 entry, so it falls back to requesting config-1. A board-specific name, or OpenWrt's own default config@1, gives Config not available and the unit will not boot from eMMC.
  • The four sds0/sds1-rx/tx-swap properties in the rtl837x node are mandatory. Without them the SoC-to-switch link still reports Link is Up - 10Gbps/Full and the driver probes normally, but no traffic crosses in either direction. Check rxdesc_* in /proc/interrupts rather than link state.
  • TX checksum offload must be disabled on a DSA conduit: the PPE checksum engine locates L3/L4 headers with its own parser, which does not understand the 4-byte Realtek tag.
  • Bridge VLAN filtering (option vlan_filtering '1' + bridge-vlan sections) works correctly on the current rtl837x driver — untagged/tagged port membership and multi-VLAN splits are both validated in production at full line rate (>900 Mbit/s). An earlier report that untagged ports still egressed tagged traffic was traced to a non-canonical config (LAN left on the base br-lan instead of the VLAN sub-device); always set network.lan.device to br-lan.<vid>, not the bridge itself.
  • MLO works with no patches: one wifi-iface listing several radios plus option mlo '1' '' and WPA3/SAE produces an ''ap-mld0 AP MLD.

An internal header provides the console at 115200 8N1, 3.3 V. The case must be opened to reach it. U-Boot autoboot is interrupted by sending the literal string gl (not Ctrl-C).

The stock ethaddr is malformed (0:0:0:0:94:83 on the unit tested), so U-Boot networking appears to come up but does not work. Set it from the MAC on the label before using ping, httpd or tftpboot:

setenv ethaddr c4:ba:26:03:94:83

With a valid MAC, U-Boot ethernet works normally — a 22 MB upload over httpd completed cleanly.

GPT on eMMC: 0:SBL1, 0:QSEE, 0:DEVCFG, 0:TME, 0:CDT, 0:APPSBLENV, 0:APPSBL, 0:ART, 0:WIFIFW, glcfg, log, 0:HLOS (kernel), rootfs.

0:ART holds per-device Wi-Fi calibration, the MAC addresses (offsets 0x4 and 0xa) and the factory regulatory country code (offset 0x88).

  • Last modified: 2026/09/25 14:04
  • by lessload