Skip to content

Commit 42eb08d

Browse files
committed
fix(rootfs/qemu-static): prefer native COMPAT over existing qemu-arm registration
When CONFIG_COMPAT runs armhf binaries natively on aarch64 (≈10× faster than qemu-user emulation), but qemu-arm is registered in kernel binfmt_misc, the previous "trust existing setup" check returned early and the build went through qemu anyway. Empirically: helios4 build 41 min via qemu vs 19 min native COMPAT on droid (RK3399). Reorder the probes: COMPAT first; if it works and qemu-arm is enabled, actively disable the binfmt_misc entry (echo 0 > /proc/.../qemu-arm). The descriptor itself is left intact — only the active flag is toggled. Gated by ARMBIAN_PREFER_NATIVE_ARMHF=no for explicit opt-out. Behaviour preserved on hosts without COMPAT. Assisted-by: Claude:claude-opus-4.7
1 parent 1d6d472 commit 42eb08d

1 file changed

Lines changed: 26 additions & 13 deletions

File tree

lib/functions/rootfs/qemu-static.sh

Lines changed: 26 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -194,26 +194,39 @@ function prepare_host_binfmt_qemu_cross() {
194194

195195
function prepare_host_binfmt_qemu_cross_arm64_host_armhf_target() {
196196
declare armhf_probe="/usr/arm-linux-gnueabihf/lib/ld-linux-armhf.so.3"
197+
declare prefer_native="${ARMBIAN_PREFER_NATIVE_ARMHF:-yes}"
198+
199+
# Probe CONFIG_COMPAT first via direct exec of ld-linux-armhf. When
200+
# COMPAT works, native armhf execution is ≈10× faster than qemu-user
201+
# emulation, so we prefer it even if qemu-arm is already registered:
202+
# kernel binfmt_misc routes armhf exec through qemu first, masking
203+
# COMPAT, so the qemu-arm entry must be actively disabled.
204+
#
205+
# `arch-test arm` is unreliable here (probes ARMv5 EABI; COMPAT runs
206+
# armhf — EABI v5+; empirically broken on Ubuntu Noble / Ampere CAX).
207+
# ld-linux-armhf comes from gcc-arm-linux-gnueabihf, an armbian host
208+
# build dep when target_arch=armhf|all.
209+
if [[ "${prefer_native}" == "yes" ]] && [[ -x "${armhf_probe}" ]] &&
210+
"${armhf_probe}" --help > /dev/null 2>&1; then
211+
if [[ -e /proc/sys/fs/binfmt_misc/qemu-arm ]] &&
212+
[[ "$(head -n1 /proc/sys/fs/binfmt_misc/qemu-arm 2> /dev/null)" == "enabled" ]]; then
213+
display_alert "Disabling qemu-arm to use native COMPAT for armhf" "≈10× faster than qemu emulation" "info"
214+
echo 0 > /proc/sys/fs/binfmt_misc/qemu-arm 2> /dev/null || true
215+
else
216+
display_alert "Host kernel can run armhf natively (CONFIG_COMPAT)" "no qemu-arm setup needed" "debug"
217+
fi
218+
return 0
219+
fi
197220

198-
# If qemu-arm is already enabled in the kernel, the native probe
199-
# below would route through qemu and lie about COMPAT. Trust the
200-
# existing setup — admin or packaged service intended it.
221+
# Native COMPAT unavailable (or opt-out via ARMBIAN_PREFER_NATIVE_ARMHF=no).
222+
# Trust an existing qemu-arm registration — admin or packaged service
223+
# intended it.
201224
if [[ -e /proc/sys/fs/binfmt_misc/qemu-arm ]] &&
202225
[[ "$(head -n1 /proc/sys/fs/binfmt_misc/qemu-arm 2> /dev/null)" == "enabled" ]]; then
203226
display_alert "qemu-arm already enabled in binfmt_misc" "trusting existing setup" "debug"
204227
return 0
205228
fi
206229

207-
# No active qemu-arm route. Probe CONFIG_COMPAT directly. `arch-test
208-
# arm` is unreliable here (probes ARMv5 EABI; COMPAT runs armhf —
209-
# EABI v5+; empirically broken on Ubuntu Noble / Ampere CAX). Direct
210-
# exec of ld-linux-armhf (from gcc-arm-linux-gnueabihf, an armbian
211-
# host build dep when target_arch=armhf|all) is authoritative.
212-
if [[ -x "${armhf_probe}" ]] && "${armhf_probe}" --help > /dev/null 2>&1; then
213-
display_alert "Host kernel can run armhf natively (CONFIG_COMPAT)" "no qemu-arm setup needed" "debug"
214-
return 0
215-
fi
216-
217230
# ld-linux-armhf may be absent on cross builds whose target isn't
218231
# armhf (gcc-arm-linux-gnueabihf isn't pulled in then). Fall back to
219232
# arch-test to avoid degraded host-capability detection on those

0 commit comments

Comments
 (0)