ndctl icon indicating copy to clipboard operation
ndctl copied to clipboard

ndctl fails to compile on musl systems due to GNU basename usage

Open NHOrus opened this issue 9 months ago • 3 comments

There are two versions of basename() function: POSIX one from libgen.c that modifies given argument, and GNU extension from string.h that doesn't. MUSL only inlcudes POSIX one, while ndctl only uses GNU extension.

https://bugs.gentoo.org/937434

NHOrus avatar Mar 30 '25 09:03 NHOrus

@NHOrus the link to https://bugs.gentoo.org/937434 is very useful but please copy at least the error message here and may a couple other relevant details too. Tentative reproduction steps would not hurt.

marc-hb avatar Apr 30 '25 18:04 marc-hb

Try to build ndctl on system that uses musl as libc. It fails to compile with error:

x86_64-pc-linux-musl-gcc -Idaxctl/daxctl.p -Idaxctl -I../ndctl-77/daxctl -I. -I../ndctl-77 -Indctl -I../ndctl-77/ndctl -I/usr/include/uuid -I/usr/include/json-c -fdiagnostics-color=always -D_FILE_OFFSET_BITS=64 -Wall -Winvalid-pch -std=gnu99 -Wchar-subscripts -Wformat-security -Wmissing-declarations -Wmissing-prototypes -Wshadow -Wsign-compare -Wstrict-prototypes -Wtype-limits -Wmaybe-uninitialized -Wdeclaration-after-statement -Wunused-result -D_FORTIFY_SOURCE=2 -include config.h -O2 -march=x86-64 -pipe -frecord-gcc-switches -fno-diagnostics-color -fmessage-length=0 -include version.h -MD -MQ daxctl/daxctl.p/device.c.o -MF daxctl/daxctl.p/device.c.o.d -o daxctl/daxctl.p/device.c.o -c ../ndctl-77/daxctl/device.c
<command-line>: warning: "_FORTIFY_SOURCE" redefined
<built-in>: note: this is the location of the previous definition
../ndctl-77/daxctl/device.c: In function 'parse_device_options':
../ndctl-77/daxctl/device.c:377:26: error: implicit declaration of function 'basename' [-Wimplicit-function-declaration]
  377 |                 device = basename(argv[0]);
      |                          ^~~~~~~~

See https://wiki.musl-libc.org/functional-differences-from-glibc.html#Miscellaneous-functions-with-GNU-quirks https://linux.die.net/man/3/basename

Musl includes POSIX version from libgen.h only, and that version modifies it's argument.

NHOrus avatar Apr 30 '25 18:04 NHOrus

https://linux.die.net/man/3/basename

OMG, what an absolute disaster... I had no idea.

These functions may return pointers to statically allocated memory which may be overwritten by subsequent calls. Alternatively, they may return a pointer to some part of path,...

With glibc, one gets the POSIX version of basename() when <libgen.h> is included, and the GNU version otherwise

In the glibc implementation of the POSIX versions of these functions they modify their argument, and segfault when called with a static string like "/usr/". Before glibc 2.2.1, the glibc version of dirname() did not correctly handle pathnames with trailing '/' characters, and generated a segfault if given a NULL argument.

Just for reference: https://pubs.opengroup.org/onlinepubs/9699919799/functions/basename.html

marc-hb avatar Apr 30 '25 19:04 marc-hb