# Pioneer Bus Router — Device Identity & Provisioning **Last updated:** 2026-07-01 **Target hardware:** GL.iNet GL-XE3000 (Puli AX), OpenWrt 21.02-SNAPSHOT, ARMv8 --- ## 1. Fleet-wide constants | Parameter | Value | |-----------|-------| | WiFi SSID (2.4 + 5 GHz) | `` — the plan spec's `X0000` shorthand means SSID = device ID (e.g. `B0042`) | | WiFi password | `Pioneer123` | | Admin username (logical) | `pioadmin` | | Admin password | `Pioneer321!` | | Admin SSH user (OpenWrt) | `root` (GL-XE3000 uses root for all admin; pioadmin is the logical name) | | Timezone | `UTC` | | Cellular APN | `fast.t-mobile.com` (T-Mobile 5G, Quectel RM520N-GL, bus `1-1.2`) | | WireGuard hub endpoint | `167.172.237.162:51820` | | WireGuard hub IP | `10.88.0.1/24` | | WireGuard tunnel subnet | `10.88.0.0/24` | | WireGuard keepalive | `25 s` | | WireGuard MTU | `1280` | | WG mwan3 fix rule | priority `99`, dest `10.88.0.0/24`, lookup `1001` (required — see §4) | | mwan3 balance mode | `balanced` (weight-based, 50/50 default; daemon adjusts live weights) | **Hub WireGuard public key:** `REPLACE_WITH_HUB_WG_PUBKEY` (Retrieve with `wg pubkey < /etc/wireguard/hub.key` on the hub at `167.172.237.162`) --- ## 2. Per-device parameters Each bus unit gets a unique identity. Fill in this table for each device: | DEVICE_ID | WG tunnel IP | WG public key | SIM 1 ICCID | SIM 2 ICCID | Notes | |-----------|-------------|---------------|-------------|-------------|-------| | `bus01` | `10.88.0.2` | *(see recon)* | `8901260417776090740F` | — | bench unit; ATT Fiber on eth0 in lab | | `B0001` | `10.88.0.3` | *(generate)* | — | — | *(first production unit)* | **Column format:** - `DEVICE_ID`: `B` + 4-digit zero-padded bus number (e.g. `B0042`) - `WG tunnel IP`: `10.88.0.X` (assigned by hub admin, no DHCP; range 10.88.0.2–10.88.0.254) - `WG private key`: base64, generated per device, never stored in this doc (keep in secrets store) - `SIM ICCID`: printed on SIM card tray ### Generating a keypair for a new device ```sh # On any Linux machine with wireguard-tools: PRIVKEY=$(wg genkey) PUBKEY=$(echo "$PRIVKEY" | wg pubkey) echo "Private: $PRIVKEY" echo "Public: $PUBKEY" ``` Register the public key + assigned IP at the hub: ```sh # On hub (167.172.237.162): wg set wg0 peer allowed-ips 10.88.0.X/32 persistent-keepalive 25 # Persist (choose ONE based on how the hub manages wg0): wg-quick save wg0 # if hub uses wg-quick # OR: edit /etc/wireguard/wg0.conf manually and run: wg addconf wg0 <(diff) # Verify hub persistence method before using wg-quick save — it overwrites the file. ``` --- ## 3. Provisioning procedure ### Prerequisites - Physical or LAN access to the router at `192.168.8.1` - Cellular SIM installed in slot 1 (provides internet for opkg) - `kit-busrouter.ipk` copied to `/tmp/kit-busrouter.ipk` on the router - Device keypair generated and hub-side peer registered (§2) ### Steps ```sh # 1. Copy provision.sh and package to the router scp scripts/provision.sh root@192.168.8.1:/tmp/provision.sh scp kit-busrouter_*.ipk root@192.168.8.1:/tmp/kit-busrouter.ipk # 2. SSH in and run ssh root@192.168.8.1 chmod +x /tmp/provision.sh /tmp/provision.sh B0042 "" "10.88.0.42" # Device reboots automatically after ~5 s. # 3. Post-reboot verification (from hub 10.88.0.1 over WireGuard) ssh root@10.88.0.42 mwan3 status # both modem_0001 and wan should appear (wan offline if no dish) cat /etc/busrouter/device-id # B0042 wg show # wgclient1 peer handshake recent ``` ### Expected WiFi after provisioning - SSID: `B0042` (same on 2.4 + 5 GHz) - Password: `Pioneer123` - LAN IP: `192.168.8.1` ### Expected admin access - SSH: `ssh root@192.168.8.1` → password `Pioneer321!` - Web UI: `http://192.168.8.1` → root / `Pioneer321!` - WG path: `ssh root@10.88.0.42` (from hub, or via WG client) --- ## 4. mwan3 + WireGuard tunnel coexistence fix **Critical — must be applied or in-tunnel SSH drops silently.** Root cause: mwan3 adds all directly-connected networks (including wgclient1's 10.88.0.0/24) to its `mwan3_connected` ipset and marks matching packets with `0x3f00`. The ip rule `9000: not from all fwmark 0/0xf000 lookup main` then routes replies via main table, which has no route for 10.88.0.0/24 (wgclient1 routes live in table 1001). Packets are silently dropped. Fix: add an ip rule at priority 99 (before mwan3's mark-based rules) routing to 10.88.0.0/24 via table 1001. `provision.sh` does this automatically: ```sh # Runtime: ip rule add to 10.88.0.0/24 priority 99 lookup 1001 # Persisted via UCI (recreated by netifd on boot): uci add network rule uci set network.@rule[-1].lookup='1001' uci set network.@rule[-1].dest='10.88.0.0/24' uci set network.@rule[-1].priority='99' uci commit network ``` Also required: `net.ipv4.conf.wgclient1.rp_filter=2` (written to /etc/sysctl.conf by provision.sh and re-asserted on WAN flap via /etc/hotplug.d/iface/99-busrouter-rpfilter). --- ## 5. GL-XE3000 hardware notes | Detail | Value | |--------|-------| | Modem | Quectel RM520N-GL (5G NR SA) | | Modem transport | MHI/PCIe (NOT USB-CDC; no `/dev/cdc-wdm*`) | | Modem bus for gl_modem | `1-1.2` (verify per unit: `ls /sys/bus/usb/devices/ | grep -v ':' | sort`) | | Signal read | `ubus call modem.signal get_signals '{"time":1}'` (primary); `gl_modem -B 1-1.2 AT AT+QCSQ` (fallback) | | GPS enable | `gl_modem -B 1-1.2 AT AT+QGPS=1` (OFF by default; provision.sh writes to /etc/rc.local) | | GPS read | `gl_modem -B 1-1.2 AT AT+QGPSLOC=2` (returns error 505/516 until first fix after GNSS enable) | | SIM switch | `gl_modem -B 1-1.2 AT AT+QUIMSLOT=<1|2>` | | SIM query | `gl_modem -B 1-1.2 AT AT+QUIMSLOT?` | | kmwan (GL multiwan) | Disabled by provision.sh — do NOT re-enable; mwan3 owns routing | | grpcurl | NOT installed; Phase 3 (Starlink) must bundle static arm64 binary in the .ipk | | setsid / nohup | ABSENT on this firmware; use `start-stop-daemon -S -b -x ` for background procs | | WG firewall zone | `wgclient1` (NOT `wan`); SSH allow rule: `src=wgclient1 src_ip=10.88.0.0/24 dest_port=22` | --- ## 6. Bench unit `bus01` — specific config | Field | Value | |-------|-------| | DEVICE_ID | `bus01` (rename to fleet format `B0001` for production) | | LAN IP | `192.168.8.1` | | WG tunnel IP | `10.88.0.2` | | Cellular (WAN1) | `rmnet_mhi0`, UCI `modem_0001`, T-Mobile CGNAT | | Starlink (WAN2) | `eth0`, UCI `wan` — no dish on bench unit; ATT Fiber used as stand-in | | WG underlay | Rides `eth0` when fiber is attached (do NOT down eth0 for bench tests) | | Access via hub | `ssh root@10.88.0.2` (from hub `10.88.0.1`) | --- ## 7. Checklist — new device before field deployment - [ ] Device ID assigned and recorded in fleet registry - [ ] WG keypair generated; public key registered at hub with assigned IP - [ ] SIM installed; APN = `fast.t-mobile.com`; cellular data confirmed - [ ] `provision.sh` run end-to-end; device rebooted cleanly - [ ] WiFi visible as ``, password `Pioneer123` - [ ] SSH to `root@192.168.8.1` succeeds with `Pioneer321!` - [ ] `mwan3 status` shows both interfaces (wan offline is OK if no dish yet) - [ ] WG tunnel up: `wg show` shows handshake < 60 s ago - [ ] Hub can SSH to `root@10.88.0.WG_IP` - [ ] `/etc/busrouter/device-id` contains correct DEVICE_ID - [ ] `busrouter` daemon running: `ps | grep daemon.sh` - [ ] Status page accessible: `http://192.168.8.1/busrouter/`