BusyBox 1.36.0 regression: Segfaults on i386 musl libc

Natanael Copa ncopa at alpinelinux.org
Fri Jan 6 09:34:15 UTC 2023


On Thu, 05 Jan 2023 21:39:09 +0100
Sören Tempel <soeren at soeren-tempel.net> wrote:

> Hi,
> 
> I am the maintainer of the BusyBox package for Alpine Linux. While
> upgrading that package from 1.35.0 to 1.36.0 I noticed a segfault
> on Alpine x86, on all other architectures BusyBox 1.36.0 builds
> fine and passes the tests. On x86 though it segfaults with any
> command-line argument, for example:
> 
> 	$ make defconfig
> 	$ make
> 	$ gdb --args ./busybox_unstripped
> 	(gdb) run
> 	Starting program: /home/buildozer/aports/main/busybox/src/build-dynamic/busybox_unstripped
> 
> 	Program received signal SIGSEGV, Segmentation fault.
> 	0xf7fc24e0 in do_relocs (dso=dso at entry=0xf7ffca20 <app>, rel=0x565578e4, rel_size=8712, stride=2) at ldso/dynlink.c:471
> 	471     ldso/dynlink.c: No such file or directory.
> 	(gdb) bt
> 	#0  0xf7fc24e0 in do_relocs (dso=dso at entry=0xf7ffca20 <app>, rel=0x565578e4, rel_size=8712, stride=2) at ldso/dynlink.c:471
> 	#1  0xf7fc263f in reloc_all (p=p at entry=0xf7ffca20 <app>) at ldso/dynlink.c:1375
> 	#2  0xf7fc473e in __dls3 (sp=0xffffdcf0, auxv=0xffffdd3c) at ldso/dynlink.c:1974
> 	#3  0xf7fc3eab in __dls2 (base=<optimized out>, sp=<optimized out>) at ldso/dynlink.c:1719
> 	#4  0xf7fc19c9 in _dlstart () from /lib/ld-musl-i386.so.1
> 
> Looking at the backtrace, it seems that it segfaults in musl's dynamic
> loader. Since BusyBox 1.35.0 worked fine on x86 I bisected this and it
> turns out that this is a regression introduced in commit
> a96ccbefe417aaac6a2ce59c788e01fc0f83902f [1]. If I disable SHA/MD5
> hardware acceleration then BusyBox 1.36.0 builds fine and passes all
> tests on Alpine Linux x86.
> 
> Any idea what particular part of the referenced commit might be causing this?

I believe this happens due to ebx is clobbered which is needed for
position independent code (PIC) on 32 bit x86.

I also wonder if the asm needs to be volatile.

Try something like this:

diff --git a/libbb/hash_md5_sha.c b/libbb/hash_md5_sha.c
index 880ffab01..d2351d3e6 100644
--- a/libbb/hash_md5_sha.c
+++ b/libbb/hash_md5_sha.c
@@ -17,8 +17,11 @@
 # if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__))
 static void cpuid(unsigned *eax, unsigned *ebx, unsigned *ecx, unsigned *edx)
 {
-       asm ("cpuid"
-               : "=a"(*eax), "=b"(*ebx), "=c"(*ecx), "=d"(*edx)
+       asm volatile (
+               "mov %%ebx, %%esi;" /* save %ebx PIC register */
+               "cpuid;"
+               "xchg %%ebx, %%esi;"
+               : "=a"(*eax), "=S"(*ebx), "=c"(*ecx), "=d"(*edx)
                : "0"(*eax),  "1"(*ebx),  "2"(*ecx),  "3"(*edx)
        );
 }

> 
> Greetings,
> Sören
> 
> [1]:
> https://git.busybox.net/busybox/commit/?id=a96ccbefe417aaac6a2ce59c788e01fc0f83902f
> _______________________________________________ busybox mailing list
> busybox at busybox.net
> http://lists.busybox.net/mailman/listinfo/busybox



More information about the busybox mailing list