diff options
-rw-r--r-- | system/musl/0001-sysconf-Add-_SC_XOPEN_UUCP.patch | 39 | ||||
-rw-r--r-- | system/musl/0002-confstr-Add-_CS_POSIX_V7_THREADS_.patch | 44 | ||||
-rw-r--r-- | system/musl/0003-pathconf-add-_PC_TIMESTAMP_RESOLUTION.patch | 29 | ||||
-rw-r--r-- | system/musl/2000-pthread-internals-increase-DEFAULT_GUARD_SIZE-to-2-p.patch | 29 | ||||
-rw-r--r-- | system/musl/APKBUILD | 158 | ||||
-rw-r--r-- | system/musl/__stack_chk_fail_local.c | 2 | ||||
-rw-r--r-- | system/musl/complex-math.patch | 59 | ||||
-rw-r--r-- | system/musl/getconf.c | 338 | ||||
-rw-r--r-- | system/musl/getent.c | 511 | ||||
-rw-r--r-- | system/musl/handle-aux-at_base.patch | 43 | ||||
-rw-r--r-- | system/musl/iconv.c | 110 | ||||
-rw-r--r-- | system/musl/ldconfig | 18 |
12 files changed, 1380 insertions, 0 deletions
diff --git a/system/musl/0001-sysconf-Add-_SC_XOPEN_UUCP.patch b/system/musl/0001-sysconf-Add-_SC_XOPEN_UUCP.patch new file mode 100644 index 000000000..67da315b6 --- /dev/null +++ b/system/musl/0001-sysconf-Add-_SC_XOPEN_UUCP.patch @@ -0,0 +1,39 @@ +From 6f592a7812de3190f567174bbb4baa40790831dd Mon Sep 17 00:00:00 2001 +From: "A. Wilcox" <AWilcox@Wilcox-Tech.com> +Date: Wed, 11 Apr 2018 23:22:33 -0500 +Subject: [PATCH 1/2] sysconf: Add _SC_XOPEN_UUCP + +We definitely don't /support/ UUCP, so return -1 for it. +But this value is required to be present in <unistd.h>. +--- + include/unistd.h | 1 + + src/conf/sysconf.c | 1 + + 2 files changed, 2 insertions(+) + +diff --git a/include/unistd.h b/include/unistd.h +index 9485da7a..2b88bbb2 100644 +--- a/include/unistd.h ++++ b/include/unistd.h +@@ -417,6 +417,7 @@ int eaccess(const char *, int); + #define _SC_XOPEN_STREAMS 246 + #define _SC_THREAD_ROBUST_PRIO_INHERIT 247 + #define _SC_THREAD_ROBUST_PRIO_PROTECT 248 ++#define _SC_XOPEN_UUCP 249 + + #define _CS_PATH 0 + #define _CS_POSIX_V6_WIDTH_RESTRICTED_ENVS 1 +diff --git a/src/conf/sysconf.c b/src/conf/sysconf.c +index 9ce330a5..58830a09 100644 +--- a/src/conf/sysconf.c ++++ b/src/conf/sysconf.c +@@ -164,6 +164,7 @@ long sysconf(int name) + [_SC_XOPEN_STREAMS] = JT_ZERO, + [_SC_THREAD_ROBUST_PRIO_INHERIT] = -1, + [_SC_THREAD_ROBUST_PRIO_PROTECT] = -1, ++ [_SC_XOPEN_UUCP] = -1, + }; + + if (name >= sizeof(values)/sizeof(values[0]) || !values[name]) { +-- +2.15.0 + diff --git a/system/musl/0002-confstr-Add-_CS_POSIX_V7_THREADS_.patch b/system/musl/0002-confstr-Add-_CS_POSIX_V7_THREADS_.patch new file mode 100644 index 000000000..ab1203cca --- /dev/null +++ b/system/musl/0002-confstr-Add-_CS_POSIX_V7_THREADS_.patch @@ -0,0 +1,44 @@ +From 94046871d24d5408adaf61941a4751c77abe06b6 Mon Sep 17 00:00:00 2001 +From: "A. Wilcox" <AWilcox@Wilcox-Tech.com> +Date: Wed, 11 Apr 2018 23:23:31 -0500 +Subject: [PATCH 2/2] confstr: Add _CS_POSIX_V7_THREADS_* + +This is used to determine what CFLAGS/LDFLAGS are needed to enable +compilation with threads on musl. We don't have any special ones, so +just return an empty string. + +This is required to be present in <unistd.h>. +--- + include/unistd.h | 2 ++ + src/conf/confstr.c | 2 +- + 2 files changed, 3 insertions(+), 1 deletion(-) + +diff --git a/include/unistd.h b/include/unistd.h +index 2b88bbb2..68686dfd 100644 +--- a/include/unistd.h ++++ b/include/unistd.h +@@ -460,6 +460,8 @@ int eaccess(const char *, int); + #define _CS_POSIX_V7_LPBIG_OFFBIG_LINTFLAGS 1147 + #define _CS_V6_ENV 1148 + #define _CS_V7_ENV 1149 ++#define _CS_POSIX_V7_THREADS_CFLAGS 1150 ++#define _CS_POSIX_V7_THREADS_LDFLAGS 1151 + + #ifdef __cplusplus + } +diff --git a/src/conf/confstr.c b/src/conf/confstr.c +index 02cb1aa2..3d417284 100644 +--- a/src/conf/confstr.c ++++ b/src/conf/confstr.c +@@ -7,7 +7,7 @@ size_t confstr(int name, char *buf, size_t len) + const char *s = ""; + if (!name) { + s = "/bin:/usr/bin"; +- } else if ((name&~4U)!=1 && name-_CS_POSIX_V6_ILP32_OFF32_CFLAGS>33U) { ++ } else if ((name&~4U)!=1 && name-_CS_POSIX_V6_ILP32_OFF32_CFLAGS>35U) { + errno = EINVAL; + return 0; + } +-- +2.15.0 + diff --git a/system/musl/0003-pathconf-add-_PC_TIMESTAMP_RESOLUTION.patch b/system/musl/0003-pathconf-add-_PC_TIMESTAMP_RESOLUTION.patch new file mode 100644 index 000000000..33b0d2379 --- /dev/null +++ b/system/musl/0003-pathconf-add-_PC_TIMESTAMP_RESOLUTION.patch @@ -0,0 +1,29 @@ +From da7bab19d59a0ea50e23371462f688329cd6c1a7 Mon Sep 17 00:00:00 2001 +From: "A. Wilcox" <AWilcox@Wilcox-Tech.com> +Date: Wed, 11 Apr 2018 23:43:19 -0500 +Subject: [PATCH 3/3] pathconf: add _PC_TIMESTAMP_RESOLUTION + +Right now, this is a worst-case assumption; some kernels may actually +have a value of 100000 here (100 Hz timers). This is considered the +easiest implementation. + +This is required to be present in <unistd.h>. +--- + include/unistd.h | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/include/unistd.h b/include/unistd.h +index 68686dfd..1bdd3292 100644 +--- a/include/unistd.h ++++ b/include/unistd.h +@@ -274,6 +274,7 @@ int eaccess(const char *, int); + #define _PC_ALLOC_SIZE_MIN 18 + #define _PC_SYMLINK_MAX 19 + #define _PC_2_SYMLINKS 20 ++#define _PC_TIMESTAMP_RESOLUTION 21 + + #define _SC_ARG_MAX 0 + #define _SC_CHILD_MAX 1 +-- +2.15.0 + diff --git a/system/musl/2000-pthread-internals-increase-DEFAULT_GUARD_SIZE-to-2-p.patch b/system/musl/2000-pthread-internals-increase-DEFAULT_GUARD_SIZE-to-2-p.patch new file mode 100644 index 000000000..b39664dac --- /dev/null +++ b/system/musl/2000-pthread-internals-increase-DEFAULT_GUARD_SIZE-to-2-p.patch @@ -0,0 +1,29 @@ +From 58dec23397e3fcc4300cc03839ce5e508389abbc Mon Sep 17 00:00:00 2001 +From: William Pitcock <nenolod@dereferenced.org> +Date: Thu, 22 Jun 2017 22:04:51 +0000 +Subject: [PATCH] pthread internals: increase DEFAULT_GUARD_SIZE to 2 pages + instead of 1 page. + +This is intended to be a proactive mitigation against any bugs similar to CVE-2017-1000366. + +Signed-off-by: William Pitcock <nenolod@dereferenced.org> +--- + src/internal/pthread_impl.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/src/internal/pthread_impl.h b/src/internal/pthread_impl.h +index ae0ab1c5..ad4ea3fa 100644 +--- a/src/internal/pthread_impl.h ++++ b/src/internal/pthread_impl.h +@@ -146,7 +146,7 @@ void __block_app_sigs(void *); + void __restore_sigs(void *); + + #define DEFAULT_STACK_SIZE 81920 +-#define DEFAULT_GUARD_SIZE 4096 ++#define DEFAULT_GUARD_SIZE 8192 + + #define __ATTRP_C11_THREAD ((void*)(uintptr_t)-1) + +-- +2.13.0 + diff --git a/system/musl/APKBUILD b/system/musl/APKBUILD new file mode 100644 index 000000000..25c93f361 --- /dev/null +++ b/system/musl/APKBUILD @@ -0,0 +1,158 @@ +# Contributor: William Pitcock <nenolod@dereferenced.org> +# Maintainer: Timo Teräs <timo.teras@iki.fi> +pkgname=musl +pkgver=1.1.19 +pkgrel=3 +pkgdesc="the musl c library (libc) implementation" +url="http://www.musl-libc.org/" +arch="all" +options="!check" +license="MIT" +depends="" +depends_dev="!uclibc-dev" +makedepends="$depends_dev" +subpackages="$pkgname-dev $pkgname-dbg libc6-compat:compat:noarch" +case "$BOOTSTRAP" in +nocc) pkgname="musl-dev"; subpackages="";; +nolibc) ;; +*) subpackages="$subpackages $pkgname-utils";; +esac +source="http://www.musl-libc.org/releases/musl-$pkgver.tar.gz + 0001-sysconf-Add-_SC_XOPEN_UUCP.patch + 0002-confstr-Add-_CS_POSIX_V7_THREADS_.patch + 0003-pathconf-add-_PC_TIMESTAMP_RESOLUTION.patch + + 2000-pthread-internals-increase-DEFAULT_GUARD_SIZE-to-2-p.patch + complex-math.patch + handle-aux-at_base.patch + + ldconfig + __stack_chk_fail_local.c + getent.c + iconv.c + " + +# secfixes: +# 1.1.15-r4: +# - CVE-2016-8859 + +builddir="$srcdir"/musl-$pkgver + +build() { + cd "$builddir" + + [ "$BOOTSTRAP" = "nocc" ] && return 0 + + # provide minimal libssp_nonshared.a so we don't need libssp from gcc + ${CROSS_COMPILE}gcc $CPPFLAGS $CFLAGS -c "$srcdir"/__stack_chk_fail_local.c -o __stack_chk_fail_local.o + ${CROSS_COMPILE}ar r libssp_nonshared.a __stack_chk_fail_local.o + + if [ "$BOOTSTRAP" != "nolibc" ]; then + # getconf/getent/iconv + local i + for i in getent iconv ; do + ${CROSS_COMPILE}gcc $CPPFLAGS $CFLAGS "$srcdir"/$i.c -o $i + done + fi + + # note: not autotools + LDFLAGS="$LDFLAGS -Wl,-soname,libc.musl-${CARCH}.so.1" \ + ./configure \ + --build=$CBUILD \ + --host=$CHOST \ + --prefix=/usr \ + --sysconfdir=/etc \ + --mandir=/usr/share/man \ + --infodir=/usr/share/info \ + --localstatedir=/var + make +} + +package() { + cd "$builddir" + + if [ "$BOOTSTRAP" = "nocc" ]; then + case "$CARCH" in + aarch64*) ARCH="aarch64" ;; + arm*) ARCH="arm" ;; + x86) ARCH="i386" ;; + x86_64) ARCH="x86_64" ;; + ppc) ARCH="powerpc" ;; + ppc64*) ARCH="powerpc64" ;; + s390*) ARCH="s390x" ;; + mips64*) ARCH="mips64" ;; + mips*) ARCH="mips" ;; + esac + + make ARCH="$ARCH" prefix=/usr DESTDIR="$pkgdir" install-headers || return 1 + else + make DESTDIR="$pkgdir" install || return 1 + + cp libssp_nonshared.a "$pkgdir"/usr/lib || return 1 + + # make LDSO the be the real file, and libc the symlink + local LDSO=$(make -f Makefile --eval "$(echo -e 'print-ldso:\n\t@echo $$(basename $(LDSO_PATHNAME))')" print-ldso) + mv -f "$pkgdir"/usr/lib/libc.so "$pkgdir"/lib/"$LDSO" || return 1 + ln -sf "$LDSO" "$pkgdir"/lib/libc.musl-${CARCH}.so.1 || return 1 + ln -sf ../../lib/"$LDSO" "$pkgdir"/usr/lib/libc.so || return 1 + mkdir -p "$pkgdir"/usr/bin || return 1 + ln -sf ../../lib/"$LDSO" "$pkgdir"/usr/bin/ldd || return 1 + fi + + # remove libintl.h, currently we don't want by default any NLS + # and use GNU gettext where needed. the plan is to migrate to + # musl gettext() later on as fully as possible. + rm "$pkgdir"/usr/include/libintl.h || return 1 +} + +utils() { + depends="!uclibc-utils scanelf" + replaces="libiconv uclibc-utils" + license="MIT BSD GPL2+" + + mkdir -p "$subpkgdir"/usr "$subpkgdir"/sbin + mv "$pkgdir"/usr/bin "$subpkgdir"/usr/ || return 1 + + install -D \ + "$builddir"/getent \ + "$builddir"/iconv \ + "$subpkgdir"/usr/bin + + install -D -m755 "$srcdir"/ldconfig "$subpkgdir"/sbin +} + +compat() { + pkgdesc="compatibility libraries for glibc" + + mkdir -p "$subpkgdir"/lib + case "$CARCH" in + armel) _ld="ld-linux.so.3" ;; + armhf | armv7) _ld="ld-linux-armhf.so.3" ;; + aarch64) _ld="ld-linux-aarch64.so.1" ;; + x86) _ld="ld-linux.so.2" ;; + x86_64) _ld="ld-linux-x86-64.so.2" + # go precompiled binary uses /lib64/ld-linux-x86-64.so.2 + # so we add a symlink + ln -s lib "$subpkgdir"/lib64 + ;; + mips* | s390*) _ld="ld.so.1" ;; + ppc64le) _ld="ld64.so.2" ;; + esac + ln -sf "/lib/libc.musl-${CARCH}.so.1" "$subpkgdir/lib/$_ld" + + for i in libc.so.6 libcrypt.so.1 libm.so.6 libpthread.so.0 librt.so.1 libutil.so.1; do + ln -sf "/lib/libc.musl-${CARCH}.so.1" "$subpkgdir/lib/$i" + done +} + +sha512sums="abee52d53af4b3c14c9088866c911a24d2b6ef67dc494f38a7a09dfe77250026f77528c24c52469c89cffa8ced2f0fa95badbdcf8d4460c90faba47e3927bcc5 musl-1.1.19.tar.gz +f274b1c3fff40494e44e68d5385d6f117bac43a10272e1415ed11d65f937e8c34639128860cff451357614a417bb9535a1c676be65a50dd33225c34f249dd4ff 0001-sysconf-Add-_SC_XOPEN_UUCP.patch +e6d7ba709a53cfefb9b5fbb4ede3bde6926504e24d5111691e4a63d15085c0e6e896a3d2df84026fad9520e08b2d98a3be901f29ee47df0bd8c58f6a34ebc49f 0002-confstr-Add-_CS_POSIX_V7_THREADS_.patch +7981521fd3aed5c6b4d6798717945ebe30de83ef327c8c6da135e6e7793f4be533833b1ff87cb25c8646c019da127e73da9adccdc7cf1f91a1ba1b60387a9e91 0003-pathconf-add-_PC_TIMESTAMP_RESOLUTION.patch +2c8e1dde1834238097b2ee8a7bfb53471a0d9cff4a5e38b55f048b567deff1cdd47c170d0578a67b1a039f95a6c5fbb8cff369c75b6a3e4d7ed171e8e86ebb8c 2000-pthread-internals-increase-DEFAULT_GUARD_SIZE-to-2-p.patch +8909dc260968770ace8f3ffdc04c6c7d20933ff115b4fa3e512fb7460860a8216c73ca7a7ad54f59cb5988ef011f02bf18aa13cc2287cc64ffdb8db84ef69d47 complex-math.patch +6a7ff16d95b5d1be77e0a0fbb245491817db192176496a57b22ab037637d97a185ea0b0d19da687da66c2a2f5578e4343d230f399d49fe377d8f008410974238 handle-aux-at_base.patch +8d3a2d5315fc56fee7da9abb8b89bb38c6046c33d154c10d168fb35bfde6b0cf9f13042a3bceee34daf091bc409d699223735dcf19f382eeee1f6be34154f26f ldconfig +062bb49fa54839010acd4af113e20f7263dde1c8a2ca359b5fb2661ef9ed9d84a0f7c3bc10c25dcfa10bb3c5a4874588dff636ac43d5dbb3d748d75400756d0b __stack_chk_fail_local.c +378d70e65bcc65bb4e1415354cecfa54b0c1146dfb24474b69e418cdbf7ad730472cd09f6f103e1c99ba6c324c9560bccdf287f5889bbc3ef0bdf0e08da47413 getent.c +9d42d66fb1facce2b85dad919be5be819ee290bd26ca2db00982b2f8e055a0196290a008711cbe2b18ec9eee8d2270e3b3a4692c5a1b807013baa5c2b70a2bbf iconv.c" diff --git a/system/musl/__stack_chk_fail_local.c b/system/musl/__stack_chk_fail_local.c new file mode 100644 index 000000000..2b403a6e0 --- /dev/null +++ b/system/musl/__stack_chk_fail_local.c @@ -0,0 +1,2 @@ +extern void __stack_chk_fail(void); +void __attribute__((visibility ("hidden"))) __stack_chk_fail_local(void) { __stack_chk_fail(); } diff --git a/system/musl/complex-math.patch b/system/musl/complex-math.patch new file mode 100644 index 000000000..fff4b59c1 --- /dev/null +++ b/system/musl/complex-math.patch @@ -0,0 +1,59 @@ +From ae2a01da2e388535da243b3d974aef74a3c06ae0 Mon Sep 17 00:00:00 2001 +From: Rich Felker <dalias@aerifal.cx> +Date: Mon, 9 Apr 2018 12:33:17 -0400 +Subject: fix wrong result in casin and many related complex functions + +the factor of -i noted in the comment at the top of casin.c was +omitted from the actual code, yielding a result rotated 90 degrees and +propagating into errors in other functions defined in terms of casin. + +implement multiplication by -i as a rotation of the real and imaginary +parts of the result, rather than by actual multiplication, since the +latter cannot be optimized without knowledge that the operand is +finite. here, the rotation is the actual intent, anyway. +--- + src/complex/casin.c | 3 ++- + src/complex/casinf.c | 3 ++- + src/complex/casinl.c | 3 ++- + 3 files changed, 6 insertions(+), 3 deletions(-) + +diff --git a/src/complex/casin.c b/src/complex/casin.c +index dfdda98..01ed618 100644 +--- a/src/complex/casin.c ++++ b/src/complex/casin.c +@@ -12,5 +12,6 @@ double complex casin(double complex z) + x = creal(z); + y = cimag(z); + w = CMPLX(1.0 - (x - y)*(x + y), -2.0*x*y); +- return clog(CMPLX(-y, x) + csqrt(w)); ++ double complex r = clog(CMPLX(-y, x) + csqrt(w)); ++ return CMPLX(cimag(r), -creal(r)); + } +diff --git a/src/complex/casinf.c b/src/complex/casinf.c +index 93f0e33..4fcb76f 100644 +--- a/src/complex/casinf.c ++++ b/src/complex/casinf.c +@@ -10,5 +10,6 @@ float complex casinf(float complex z) + x = crealf(z); + y = cimagf(z); + w = CMPLXF(1.0 - (x - y)*(x + y), -2.0*x*y); +- return clogf(CMPLXF(-y, x) + csqrtf(w)); ++ float complex r = clogf(CMPLXF(-y, x) + csqrtf(w)); ++ return CMPLXF(cimagf(r), -crealf(r)); + } +diff --git a/src/complex/casinl.c b/src/complex/casinl.c +index 0916c60..3b7ceba 100644 +--- a/src/complex/casinl.c ++++ b/src/complex/casinl.c +@@ -15,6 +15,7 @@ long double complex casinl(long double complex z) + x = creall(z); + y = cimagl(z); + w = CMPLXL(1.0 - (x - y)*(x + y), -2.0*x*y); +- return clogl(CMPLXL(-y, x) + csqrtl(w)); ++ long double complex r = clogl(CMPLXL(-y, x) + csqrtl(w)); ++ return CMPLXL(cimagl(r), -creall(r)); + } + #endif +-- +cgit v0.11.2 + diff --git a/system/musl/getconf.c b/system/musl/getconf.c new file mode 100644 index 000000000..c4235242b --- /dev/null +++ b/system/musl/getconf.c @@ -0,0 +1,338 @@ +/*- + * Copyright (c) 1996, 1998 The NetBSD Foundation, Inc. + * All rights reserved. + * + * This code is derived from software contributed to The NetBSD Foundation + * by J.T. Conklin. + * + * Mostly rewritten to be used in Alpine Linux (with musl c-library) + * by Timo Teräs. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS + * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#include <err.h> +#include <errno.h> +#include <values.h> +#include <limits.h> +#include <locale.h> +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <string.h> + +struct conf_variable { + const char *name; + enum { SYSCONF, CONFSTR, PATHCONF, CONSTANT, UCONSTANT, NUM_TYPES } type; + long value; +}; + +static const struct conf_variable conf_table[] = { +{ "PATH", CONFSTR, _CS_PATH }, + +/* Utility Limit Minimum Values */ +{ "POSIX2_BC_BASE_MAX", CONSTANT, _POSIX2_BC_BASE_MAX }, +{ "POSIX2_BC_DIM_MAX", CONSTANT, _POSIX2_BC_DIM_MAX }, +{ "POSIX2_BC_SCALE_MAX", CONSTANT, _POSIX2_BC_SCALE_MAX }, +{ "POSIX2_BC_STRING_MAX", CONSTANT, _POSIX2_BC_STRING_MAX }, +{ "POSIX2_COLL_WEIGHTS_MAX", CONSTANT, _POSIX2_COLL_WEIGHTS_MAX }, +{ "POSIX2_EXPR_NEST_MAX", CONSTANT, _POSIX2_EXPR_NEST_MAX }, +{ "POSIX2_LINE_MAX", CONSTANT, _POSIX2_LINE_MAX }, +{ "POSIX2_RE_DUP_MAX", CONSTANT, _POSIX2_RE_DUP_MAX }, +{ "POSIX2_VERSION", CONSTANT, _POSIX2_VERSION }, + +/* POSIX.1 Minimum Values */ +{ "_POSIX_AIO_LISTIO_MAX", CONSTANT, _POSIX_AIO_LISTIO_MAX }, +{ "_POSIX_AIO_MAX", CONSTANT, _POSIX_AIO_MAX }, +{ "_POSIX_ARG_MAX", CONSTANT, _POSIX_ARG_MAX }, +{ "_POSIX_CHILD_MAX", CONSTANT, _POSIX_CHILD_MAX }, +{ "_POSIX_LINK_MAX", CONSTANT, _POSIX_LINK_MAX }, +{ "_POSIX_MAX_CANON", CONSTANT, _POSIX_MAX_CANON }, +{ "_POSIX_MAX_INPUT", CONSTANT, _POSIX_MAX_INPUT }, +{ "_POSIX_MQ_OPEN_MAX", CONSTANT, _POSIX_MQ_OPEN_MAX }, +{ "_POSIX_MQ_PRIO_MAX", CONSTANT, _POSIX_MQ_PRIO_MAX }, +{ "_POSIX_NAME_MAX", CONSTANT, _POSIX_NAME_MAX }, +{ "_POSIX_NGROUPS_MAX", CONSTANT, _POSIX_NGROUPS_MAX }, +{ "_POSIX_OPEN_MAX", CONSTANT, _POSIX_OPEN_MAX }, +{ "_POSIX_PATH_MAX", CONSTANT, _POSIX_PATH_MAX }, +{ "_POSIX_PIPE_BUF", CONSTANT, _POSIX_PIPE_BUF }, +{ "_POSIX_SSIZE_MAX", CONSTANT, _POSIX_SSIZE_MAX }, +{ "_POSIX_STREAM_MAX", CONSTANT, _POSIX_STREAM_MAX }, +{ "_POSIX_TZNAME_MAX", CONSTANT, _POSIX_TZNAME_MAX }, + +/* Symbolic Utility Limits */ +{ "BC_BASE_MAX", SYSCONF, _SC_BC_BASE_MAX }, +{ "BC_DIM_MAX", SYSCONF, _SC_BC_DIM_MAX }, +{ "BC_SCALE_MAX", SYSCONF, _SC_BC_SCALE_MAX }, +{ "BC_STRING_MAX", SYSCONF, _SC_BC_STRING_MAX }, +{ "COLL_WEIGHTS_MAX", SYSCONF, _SC_COLL_WEIGHTS_MAX }, +{ "EXPR_NEST_MAX", SYSCONF, _SC_EXPR_NEST_MAX }, +{ "LINE_MAX", SYSCONF, _SC_LINE_MAX }, +{ "RE_DUP_MAX", SYSCONF, _SC_RE_DUP_MAX }, + +/* Optional Facility Configuration Values */ +{ "_POSIX2_C_BIND", SYSCONF, _SC_2_C_BIND }, +{ "POSIX2_C_DEV", SYSCONF, _SC_2_C_DEV }, +{ "POSIX2_CHAR_TERM", SYSCONF, _SC_2_CHAR_TERM }, +{ "POSIX2_FORT_DEV", SYSCONF, _SC_2_FORT_DEV }, +{ "POSIX2_FORT_RUN", SYSCONF, _SC_2_FORT_RUN }, +{ "POSIX2_LOCALEDEF", SYSCONF, _SC_2_LOCALEDEF }, +{ "POSIX2_SW_DEV", SYSCONF, _SC_2_SW_DEV }, +{ "POSIX2_UPE", SYSCONF, _SC_2_UPE }, + +/* POSIX.1 Configurable System Variables */ +{ "AIO_LISTIO_MAX", SYSCONF, _SC_AIO_LISTIO_MAX }, +{ "AIO_MAX", SYSCONF, _SC_AIO_MAX }, +{ "ARG_MAX", SYSCONF, _SC_ARG_MAX }, +{ "CHILD_MAX", SYSCONF, _SC_CHILD_MAX }, +{ "CLK_TCK", SYSCONF, _SC_CLK_TCK }, +{ "MQ_OPEN_MAX", SYSCONF, _SC_MQ_OPEN_MAX }, +{ "MQ_PRIO_MAX", SYSCONF, _SC_MQ_PRIO_MAX }, +{ "NGROUPS_MAX", SYSCONF, _SC_NGROUPS_MAX }, +{ "OPEN_MAX", SYSCONF, _SC_OPEN_MAX }, +{ "STREAM_MAX", SYSCONF, _SC_STREAM_MAX }, +{ "TZNAME_MAX", SYSCONF, _SC_TZNAME_MAX }, +{ "_POSIX_JOB_CONTROL", SYSCONF, _SC_JOB_CONTROL }, +{ "_POSIX_SAVED_IDS", SYSCONF, _SC_SAVED_IDS }, +{ "_POSIX_VERSION", SYSCONF, _SC_VERSION }, + +{ "LINK_MAX", PATHCONF, _PC_LINK_MAX }, +{ "MAX_CANON", PATHCONF, _PC_MAX_CANON }, +{ "MAX_INPUT", PATHCONF, _PC_MAX_INPUT }, +{ "NAME_MAX", PATHCONF, _PC_NAME_MAX }, +{ "PATH_MAX", PATHCONF, _PC_PATH_MAX }, +{ "PIPE_BUF", PATHCONF, _PC_PIPE_BUF }, +{ "_POSIX_CHOWN_RESTRICTED", PATHCONF, _PC_CHOWN_RESTRICTED }, +{ "_POSIX_NO_TRUNC", PATHCONF, _PC_NO_TRUNC }, +{ "_POSIX_VDISABLE", PATHCONF, _PC_VDISABLE }, + +/* POSIX.1b Configurable System Variables */ +{ "PAGESIZE", SYSCONF, _SC_PAGESIZE }, +{ "_POSIX_ASYNCHRONOUS_IO", SYSCONF, _SC_ASYNCHRONOUS_IO }, +{ "_POSIX_FSYNC", SYSCONF, _SC_FSYNC }, +{ "_POSIX_MAPPED_FILES", SYSCONF, _SC_MAPPED_FILES }, +{ "_POSIX_MEMLOCK", SYSCONF, _SC_MEMLOCK }, +{ "_POSIX_MEMLOCK_RANGE", SYSCONF, _SC_MEMLOCK_RANGE }, +{ "_POSIX_MEMORY_PROTECTION", SYSCONF, _SC_MEMORY_PROTECTION }, +{ "_POSIX_MESSAGE_PASSING", SYSCONF, _SC_MESSAGE_PASSING }, +{ "_POSIX_MONOTONIC_CLOCK", SYSCONF, _SC_MONOTONIC_CLOCK }, +{ "_POSIX_PRIORITY_SCHEDULING", SYSCONF, _SC_PRIORITY_SCHEDULING }, +{ "_POSIX_SEMAPHORES", SYSCONF, _SC_SEMAPHORES }, +{ "_POSIX_SHARED_MEMORY_OBJECTS", SYSCONF, _SC_SHARED_MEMORY_OBJECTS }, +{ "_POSIX_SYNCHRONIZED_IO", SYSCONF, _SC_SYNCHRONIZED_IO }, +{ "_POSIX_TIMERS", SYSCONF, _SC_TIMERS }, + +{ "_POSIX_SYNC_IO", PATHCONF, _PC_SYNC_IO }, + +/* POSIX.1c Configurable System Variables */ +{ "LOGIN_NAME_MAX", SYSCONF, _SC_LOGIN_NAME_MAX }, +{ "_POSIX_THREADS", SYSCONF, _SC_THREADS }, + +/* POSIX.1j Configurable System Variables */ +{ "_POSIX_BARRIERS", SYSCONF, _SC_BARRIERS }, +{ "_POSIX_READER_WRITER_LOCKS", SYSCONF, _SC_READER_WRITER_LOCKS }, +{ "_POSIX_SPIN_LOCKS", SYSCONF, _SC_SPIN_LOCKS }, + +/* XPG4.2 Configurable System Variables */ +{ "IOV_MAX", SYSCONF, _SC_IOV_MAX }, +{ "PAGE_SIZE", SYSCONF, _SC_PAGE_SIZE }, +{ "_XOPEN_SHM", SYSCONF, _SC_XOPEN_SHM }, + +/* X/Open CAE Spec. Issue 5 Version 2 Configurable System Variables */ +{ "FILESIZEBITS", PATHCONF, _PC_FILESIZEBITS }, + +/* POSIX.1-2001 XSI Option Group Configurable System Variables */ +{ "ATEXIT_MAX", SYSCONF, _SC_ATEXIT_MAX }, + +/* POSIX.1-2001 TSF Configurable System Variables */ +{ "GETGR_R_SIZE_MAX", SYSCONF, _SC_GETGR_R_SIZE_MAX }, +{ "GETPW_R_SIZE_MAX", SYSCONF, _SC_GETPW_R_SIZE_MAX }, + +/* Commonly provided extensions */ +{ "_PHYS_PAGES", SYSCONF, _SC_PHYS_PAGES }, +{ "_AVPHYS_PAGES", SYSCONF, _SC_AVPHYS_PAGES }, +{ "_NPROCESSORS_CONF", SYSCONF, _SC_NPROCESSORS_CONF }, +{ "_NPROCESSORS_ONLN", SYSCONF, _SC_NPROCESSORS_ONLN }, + +/* Data type related extensions */ +{ "CHAR_BIT", CONSTANT, CHAR_BIT }, +{ "CHAR_MAX", CONSTANT, CHAR_MAX }, +{ "CHAR_MIN", CONSTANT, CHAR_MIN }, +{ "INT_MAX", CONSTANT, INT_MAX }, +{ "INT_MIN", CONSTANT, INT_MIN }, +{ "LONG_BIT", CONSTANT, LONG_BIT }, +{ "LONG_MAX", CONSTANT, LONG_MAX }, +{ "LONG_MIN", CONSTANT, LONG_MIN }, +{ "SCHAR_MAX", CONSTANT, SCHAR_MAX }, +{ "SCHAR_MIN", CONSTANT, SCHAR_MIN }, +{ "SHRT_MAX", CONSTANT, SHRT_MAX }, +{ "SHRT_MIN", CONSTANT, SHRT_MIN }, +{ "SSIZE_MAX", CONSTANT, SSIZE_MAX }, +{ "UCHAR_MAX", UCONSTANT, (long) UCHAR_MAX }, +{ "UINT_MAX", UCONSTANT, (long) UINT_MAX }, +{ "ULONG_MAX", UCONSTANT, (long) ULONG_MAX }, +{ "USHRT_MAX", UCONSTANT, (long) USHRT_MAX }, +{ "WORD_BIT", CONSTANT, WORD_BIT }, + +{ NULL, CONSTANT, 0L } +}; + +static int all = 0; + +static void usage(const char *p) +{ + (void)fprintf(stderr, "Usage: %s system_var\n\t%s -a\n" + "\t%s path_var pathname\n\t%s -a pathname\n", p, p, p, p); + exit(EXIT_FAILURE); +} + +static void print_long(const char *name, long val) +{ + if (all) printf("%s = %ld\n", name, val); + else printf("%ld\n", val); +} + +static void print_ulong(const char *name, unsigned long val) +{ + if (all) printf("%s = %lu\n", name, val); + else printf("%lu\n", val); +} + +static void print_string(const char *name, const char *val) +{ + if (all) printf("%s = %s\n", name, val); + else printf("%s\n", val); +} + +static int print_constant(const struct conf_variable *cp, const char *pathname) +{ + print_long(cp->name, cp->value); + return 0; +} + +static int print_uconstant(const struct conf_variable *cp, const char *pathname) +{ + print_ulong(cp->name, (unsigned long) cp->value); + return 0; +} + +static int print_sysconf(const struct conf_variable *cp, const char *pathname) +{ + long val; + + errno = 0; + if ((val = sysconf((int)cp->value)) == -1) { + if (errno != 0) err(EXIT_FAILURE, "sysconf(%ld)", cp->value); + return -1; + } + print_long(cp->name, val); + return 0; +} + +static int print_confstr(const struct conf_variable *cp, const char *pathname) +{ + size_t len; + char *val; + + errno = 0; + if ((len = confstr((int)cp->value, NULL, 0)) == 0) goto error; + if ((val = malloc(len)) == NULL) err(EXIT_FAILURE, "Can't allocate %zu bytes", len); + errno = 0; + if (confstr((int)cp->value, val, len) == 0) goto error; + print_string(cp->name, val); + free(val); + return 0; +error: + if (errno != EINVAL) err(EXIT_FAILURE, "confstr(%ld)", cp->value); + return -1; +} + +static int print_pathconf(const struct conf_variable *cp, const char *pathname) +{ + long val; + + errno = 0; + if ((val = pathconf(pathname, (int)cp->value)) == -1) { + if (all && errno == EINVAL) return 0; + if (errno != 0) err(EXIT_FAILURE, "pathconf(%s, %ld)", pathname, cp->value); + return -1; + } + print_long(cp->name, val); + return 0; +} + +typedef int (*handler_t)(const struct conf_variable *cp, const char *pathname); +static const handler_t type_handlers[NUM_TYPES] = { + [SYSCONF] = print_sysconf, + [CONFSTR] = print_confstr, + [PATHCONF] = print_pathconf, + [CONSTANT] = print_constant, + [UCONSTANT] = print_uconstant, +}; + +int main(int argc, char **argv) +{ + const char *progname = argv[0]; + const struct conf_variable *cp; + const char *varname, *pathname; + int ch, found = 0; + + (void)setlocale(LC_ALL, ""); + while ((ch = getopt(argc, argv, "a")) != -1) { + switch (ch) { + case 'a': + all = 1; + break; + case '?': + default: + usage(progname); + } + } + argc -= optind; + argv += optind; + + if (!all) { + if (argc == 0) + usage(progname); + varname = argv[0]; + argc--; + argv++; + } else + varname = NULL; + + if (argc > 1) + usage(progname); + pathname = argv[0]; /* may be NULL */ + + for (cp = conf_table; cp->name != NULL; cp++) { + if (!all && strcmp(varname, cp->name) != 0) continue; + if ((cp->type == PATHCONF) == (pathname != NULL)) { + if (type_handlers[cp->type](cp, pathname) < 0) + print_string(cp->name, "undefined"); + found = 1; + } else if (!all) + errx(EXIT_FAILURE, "%s: invalid variable type", cp->name); + } + if (!all && !found) errx(EXIT_FAILURE, "%s: unknown variable", varname); + (void)fflush(stdout); + return ferror(stdout) ? EXIT_FAILURE : EXIT_SUCCESS; +} diff --git a/system/musl/getent.c b/system/musl/getent.c new file mode 100644 index 000000000..b10d75acc --- /dev/null +++ b/system/musl/getent.c @@ -0,0 +1,511 @@ +/*- + * Copyright (c) 2004-2006 The NetBSD Foundation, Inc. + * All rights reserved. + * + * This code is derived from software contributed to The NetBSD Foundation + * by Luke Mewburn. + * Timo Teräs cleaned up the code for use in Alpine Linux with musl libc. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS + * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#include <sys/socket.h> +#include <sys/param.h> +#include <ctype.h> +#include <errno.h> +#include <limits.h> +#include <netdb.h> +#include <pwd.h> +#include <grp.h> +#include <stdio.h> +#include <stdarg.h> +#include <stdbool.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> +#include <paths.h> +#include <err.h> + +#include <arpa/inet.h> +#include <arpa/nameser.h> + +#include <net/if.h> +#include <net/ethernet.h> +#include <netinet/ether.h> +#include <netinet/in.h> + +enum { + RV_OK = 0, + RV_USAGE = 1, + RV_NOTFOUND = 2, + RV_NOENUM = 3 +}; + +static int usage(const char *); + +static int parsenum(const char *word, unsigned long *result) +{ + unsigned long num; + char *ep; + + if (!isdigit((unsigned char)word[0])) + return 0; + errno = 0; + num = strtoul(word, &ep, 10); + if (num == ULONG_MAX && errno == ERANGE) + return 0; + if (*ep != '\0') + return 0; + *result = num; + return 1; +} + +/* + * printfmtstrings -- + * vprintf(format, ...), + * then the aliases (beginning with prefix, separated by sep), + * then a newline + */ +__attribute__ ((format (printf, 4, 5))) +static void printfmtstrings(char *strings[], const char *prefix, const char *sep, + const char *fmt, ...) +{ + va_list ap; + const char *curpref; + size_t i; + + va_start(ap, fmt); + (void)vprintf(fmt, ap); + va_end(ap); + + curpref = prefix; + for (i = 0; strings[i] != NULL; i++) { + (void)printf("%s%s", curpref, strings[i]); + curpref = sep; + } + (void)printf("\n"); +} + +static int ethers(int argc, char *argv[]) +{ + char hostname[MAXHOSTNAMELEN + 1], *hp; + struct ether_addr ea, *eap; + int i, rv; + + if (argc == 2) { + warnx("Enumeration not supported on ethers"); + return RV_NOENUM; + } + + rv = RV_OK; + for (i = 2; i < argc; i++) { + if ((eap = ether_aton(argv[i])) == NULL) { + eap = &ea; + hp = argv[i]; + if (ether_hostton(hp, eap) != 0) { + rv = RV_NOTFOUND; + break; + } + } else { + hp = hostname; + if (ether_ntohost(hp, eap) != 0) { + rv = RV_NOTFOUND; + break; + } + } + (void)printf("%-17s %s\n", ether_ntoa(eap), hp); + } + return rv; +} + +static void groupprint(const struct group *gr) +{ + printfmtstrings(gr->gr_mem, ":", ",", "%s:%s:%u", + gr->gr_name, gr->gr_passwd, gr->gr_gid); +} + +static int group(int argc, char *argv[]) +{ + struct group *gr; + unsigned long id; + int i, rv; + + rv = RV_OK; + if (argc == 2) { + while ((gr = getgrent()) != NULL) + groupprint(gr); + } else { + for (i = 2; i < argc; i++) { + if (parsenum(argv[i], &id)) + gr = getgrgid((gid_t)id); + else + gr = getgrnam(argv[i]); + if (gr == NULL) { + rv = RV_NOTFOUND; + break; + } + groupprint(gr); + } + } + endgrent(); + return rv; +} + +static void hostsprint(const struct hostent *he) +{ + char buf[INET6_ADDRSTRLEN]; + + if (inet_ntop(he->h_addrtype, he->h_addr, buf, sizeof(buf)) == NULL) + (void)strlcpy(buf, "# unknown", sizeof(buf)); + printfmtstrings(he->h_aliases, " ", " ", "%-16s %s", buf, he->h_name); +} + +static int hosts(int argc, char *argv[]) +{ + struct hostent *he; + char addr[IN6ADDRSZ]; + int i, rv; + + sethostent(1); + rv = RV_OK; + if (argc == 2) { + while ((he = gethostent()) != NULL) + hostsprint(he); + } else { + for (i = 2; i < argc; i++) { + if (inet_pton(AF_INET6, argv[i], (void *)addr) > 0) + he = gethostbyaddr(addr, IN6ADDRSZ, AF_INET6); + else if (inet_pton(AF_INET, argv[i], (void *)addr) > 0) + he = gethostbyaddr(addr, INADDRSZ, AF_INET); + else if ((he = gethostbyname2(argv[i], AF_INET6)) == NULL) + he = gethostbyname2(argv[i], AF_INET); + if (he == NULL) { + rv = RV_NOTFOUND; + break; + } + hostsprint(he); + } + } + endhostent(); + return rv; +} + +static int ahosts_ex(int family, int flags, int argc, char *argv[]) +{ + static const char *socktypes[] = { + [SOCK_STREAM] = "STREAM", + [SOCK_DGRAM] = "DGRAM", + [SOCK_RAW] = "RAW", + [SOCK_RDM] = "RDM", + [SOCK_SEQPACKET] = "SEQPACKET", + [SOCK_DCCP] = "DCCP", + [SOCK_PACKET] = "PACKET", + }; + const char *sockstr; + char sockbuf[16], buf[INET6_ADDRSTRLEN]; + struct addrinfo *res, *r, hint; + void *addr; + int i; + + if (argc == 2) + return hosts(argc, argv); + + hint = (struct addrinfo) { + .ai_family = family, + .ai_flags = AI_ADDRCONFIG | AI_CANONNAME | flags, + }; + + for (i = 2; i < argc; i++) { + if (getaddrinfo(argv[i], 0, &hint, &res) != 0) + return RV_NOTFOUND; + + for (r = res; r; r = r->ai_next) { + sockstr = NULL; + if (r->ai_socktype >= 0 && r->ai_socktype < sizeof(socktypes)/sizeof(socktypes[0])) + sockstr = socktypes[r->ai_socktype]; + if (!sockstr) { + sprintf(buf, "%d", r->ai_socktype); + sockstr = sockbuf; + } + switch (r->ai_family) { + case AF_INET: + addr = &((struct sockaddr_in*) r->ai_addr)->sin_addr; + break; + case AF_INET6: + addr = &((struct sockaddr_in6*) r->ai_addr)->sin6_addr; + break; + default: + continue; + } + if (inet_ntop(r->ai_family, addr, buf, sizeof(buf)) == NULL) + (void)strlcpy(buf, "# unknown", sizeof(buf)); + printf("%-15s %-6s %s\n", buf, sockstr, r->ai_canonname ?: ""); + } + } + + return RV_OK; +} + +static int ahosts(int argc, char *argv[]) +{ + return ahosts_ex(AF_UNSPEC, 0, argc, argv); +} + +static int ahostsv4(int argc, char *argv[]) +{ + return ahosts_ex(AF_INET, 0, argc, argv); +} + +static int ahostsv6(int argc, char *argv[]) +{ + return ahosts_ex(AF_INET6, AI_V4MAPPED, argc, argv); +} + +static void networksprint(const struct netent *ne) +{ + char buf[INET6_ADDRSTRLEN]; + struct in_addr ianet; + + ianet = inet_makeaddr(ne->n_net, 0); + if (inet_ntop(ne->n_addrtype, &ianet, buf, sizeof(buf)) == NULL) + (void)strlcpy(buf, "# unknown", sizeof(buf)); + printfmtstrings(ne->n_aliases, " ", " ", "%-16s %s", ne->n_name, buf); +} + +static int networks(int argc, char *argv[]) +{ + struct netent *ne; + in_addr_t net; + int i, rv; + + setnetent(1); + rv = RV_OK; + if (argc == 2) { + while ((ne = getnetent()) != NULL) + networksprint(ne); + } else { + for (i = 2; i < argc; i++) { + net = inet_network(argv[i]); + if (net != INADDR_NONE) + ne = getnetbyaddr(net, AF_INET); + else + ne = getnetbyname(argv[i]); + if (ne != NULL) { + rv = RV_NOTFOUND; + break; + } + networksprint(ne); + } + } + endnetent(); + return rv; +} + +static void passwdprint(struct passwd *pw) +{ + (void)printf("%s:%s:%u:%u:%s:%s:%s\n", + pw->pw_name, pw->pw_passwd, pw->pw_uid, + pw->pw_gid, pw->pw_gecos, pw->pw_dir, pw->pw_shell); +} + +static int passwd(int argc, char *argv[]) +{ + struct passwd *pw; + unsigned long id; + int i, rv; + + rv = RV_OK; + if (argc == 2) { + while ((pw = getpwent()) != NULL) + passwdprint(pw); + } else { + for (i = 2; i < argc; i++) { + if (parsenum(argv[i], &id)) + pw = getpwuid((uid_t)id); + else + pw = getpwnam(argv[i]); + if (pw == NULL) { + rv = RV_NOTFOUND; + break; + } + passwdprint(pw); + } + } + endpwent(); + return rv; +} + +static void protocolsprint(struct protoent *pe) +{ + printfmtstrings(pe->p_aliases, " ", " ", + "%-16s %5d", pe->p_name, pe->p_proto); +} + +static int protocols(int argc, char *argv[]) +{ + struct protoent *pe; + unsigned long id; + int i, rv; + + setprotoent(1); + rv = RV_OK; + if (argc == 2) { + while ((pe = getprotoent()) != NULL) + protocolsprint(pe); + } else { + for (i = 2; i < argc; i++) { + if (parsenum(argv[i], &id)) + pe = getprotobynumber((int)id); + else + pe = getprotobyname(argv[i]); + if (pe == NULL) { + rv = RV_NOTFOUND; + break; + } + protocolsprint(pe); + } + } + endprotoent(); + return rv; +} + +static void servicesprint(struct servent *se) +{ + printfmtstrings(se->s_aliases, " ", " ", + "%-16s %5d/%s", + se->s_name, ntohs(se->s_port), se->s_proto); + +} + +static int services(int argc, char *argv[]) +{ + struct servent *se; + unsigned long id; + char *proto; + int i, rv; + + setservent(1); + rv = RV_OK; + if (argc == 2) { + while ((se = getservent()) != NULL) + servicesprint(se); + } else { + for (i = 2; i < argc; i++) { + proto = strchr(argv[i], '/'); + if (proto != NULL) + *proto++ = '\0'; + if (parsenum(argv[i], &id)) + se = getservbyport(htons(id), proto); + else + se = getservbyname(argv[i], proto); + if (se == NULL) { + rv = RV_NOTFOUND; + break; + } + servicesprint(se); + } + } + endservent(); + return rv; +} + +static int shells(int argc, char *argv[]) +{ + const char *sh; + int i, rv; + + setusershell(); + rv = RV_OK; + if (argc == 2) { + while ((sh = getusershell()) != NULL) + (void)printf("%s\n", sh); + } else { + for (i = 2; i < argc; i++) { + setusershell(); + while ((sh = getusershell()) != NULL) { + if (strcmp(sh, argv[i]) == 0) { + (void)printf("%s\n", sh); + break; + } + } + if (sh == NULL) { + rv = RV_NOTFOUND; + break; + } + } + } + endusershell(); + return rv; +} + +static struct getentdb { + const char *name; + int (*callback)(int, char *[]); +} databases[] = { + { "ethers", ethers, }, + { "group", group, }, + { "hosts", hosts, }, + { "ahosts", ahosts, }, + { "ahostsv4", ahostsv4, }, + { "ahostsv6", ahostsv6, }, + { "networks", networks, }, + { "passwd", passwd, }, + { "protocols", protocols, }, + { "services", services, }, + { "shells", shells, }, + + { NULL, NULL, }, +}; + +static int usage(const char *arg0) +{ + struct getentdb *curdb; + size_t i; + + (void)fprintf(stderr, "Usage: %s database [key ...]\n", arg0); + (void)fprintf(stderr, "\tdatabase may be one of:"); + for (i = 0, curdb = databases; curdb->name != NULL; curdb++, i++) { + if (i % 7 == 0) + (void)fputs("\n\t\t", stderr); + (void)fprintf(stderr, "%s%s", i % 7 == 0 ? "" : " ", + curdb->name); + } + (void)fprintf(stderr, "\n"); + exit(RV_USAGE); + /* NOTREACHED */ +} + +int +main(int argc, char *argv[]) +{ + struct getentdb *curdb; + + if (argc < 2) + usage(argv[0]); + for (curdb = databases; curdb->name != NULL; curdb++) + if (strcmp(curdb->name, argv[1]) == 0) + return (*curdb->callback)(argc, argv); + + warn("Unknown database `%s'", argv[1]); + usage(argv[0]); + /* NOTREACHED */ +} diff --git a/system/musl/handle-aux-at_base.patch b/system/musl/handle-aux-at_base.patch new file mode 100644 index 000000000..c16463824 --- /dev/null +++ b/system/musl/handle-aux-at_base.patch @@ -0,0 +1,43 @@ +diff --git a/src/env/__init_tls.c b/src/env/__init_tls.c +index b125eb1..616c6a6 100644 +--- a/src/env/__init_tls.c ++++ b/src/env/__init_tls.c +@@ -66,8 +66,10 @@ void *__copy_tls(unsigned char *mem) + } + + #if ULONG_MAX == 0xffffffff ++typedef Elf32_Ehdr Ehdr; + typedef Elf32_Phdr Phdr; + #else ++typedef Elf64_Ehdr Ehdr; + typedef Elf64_Phdr Phdr; + #endif + +@@ -77,15 +79,23 @@ extern const size_t _DYNAMIC[]; + static void static_init_tls(size_t *aux) + { + unsigned char *p; +- size_t n; ++ size_t n, e; + Phdr *phdr, *tls_phdr=0; + size_t base = 0; + void *mem; + +- for (p=(void *)aux[AT_PHDR],n=aux[AT_PHNUM]; n; n--,p+=aux[AT_PHENT]) { ++ if (aux[AT_BASE]) { ++ Ehdr *ehdr = (void *)aux[AT_BASE]; ++ p = (unsigned char *)aux[AT_BASE] + ehdr->e_phoff; ++ n = ehdr->e_phnum; ++ e = ehdr->e_phentsize; ++ } else { ++ p = (void *)aux[AT_PHDR]; ++ n = aux[AT_PHNUM]; ++ e = aux[AT_PHENT]; ++ } ++ for (; n; n--, p+=e) { + phdr = (void *)p; +- if (phdr->p_type == PT_PHDR) +- base = aux[AT_PHDR] - phdr->p_vaddr; + if (phdr->p_type == PT_DYNAMIC && _DYNAMIC) + base = (size_t)_DYNAMIC - phdr->p_vaddr; + if (phdr->p_type == PT_TLS) diff --git a/system/musl/iconv.c b/system/musl/iconv.c new file mode 100644 index 000000000..f5d5ce2aa --- /dev/null +++ b/system/musl/iconv.c @@ -0,0 +1,110 @@ +/* + * iconv.c + * Implementation of SUSv4 XCU iconv utility + * Copyright © 2011 Rich Felker + * Licensed under the terms of the GNU General Public License, v2 or later + */ + +#include <stdlib.h> +#include <stdio.h> +#include <iconv.h> +#include <locale.h> +#include <langinfo.h> +#include <unistd.h> +#include <errno.h> +#include <string.h> + +int main(int argc, char **argv) +{ + const char *from=0, *to=0; + int b; + iconv_t cd; + char buf[BUFSIZ]; + char outbuf[BUFSIZ*4]; + char *in, *out; + size_t inb; + size_t l; + size_t unitsize=0; + int err=0; + FILE *f; + + while ((b = getopt(argc, argv, "f:t:csl")) != EOF) switch(b) { + case 'l': + puts("UTF-8, UTF-16BE, UTF-16LE, UTF-32BE, UTF32-LE, UCS-2BE, UCS-2LE, WCHAR_T,\n" + "US_ASCII, ISO8859-1, ISO8859-2, ISO8859-3, ISO8859-4, ISO8859-5,\n" + "ISO8859-6, ISO8859-7, ..."); + exit(0); + case 'c': case 's': break; + case 'f': from=optarg; break; + case 't': to=optarg; break; + default: exit(1); + } + + if (!from || !to) { + setlocale(LC_CTYPE, ""); + if (!to) to = nl_langinfo(CODESET); + if (!from) from = nl_langinfo(CODESET); + } + cd = iconv_open(to, from); + if (cd == (iconv_t)-1) { + if (iconv_open(to, "WCHAR_T") == (iconv_t)-1) + fprintf(stderr, "iconv: destination charset %s: ", to); + else + fprintf(stderr, "iconv: source charset %s: ", from); + perror(""); + exit(1); + } + if (optind == argc) argv[argc++] = "-"; + + for (; optind < argc; optind++) { + if (argv[optind][0]=='-' && !argv[optind][1]) { + f = stdin; + argv[optind] = "(stdin)"; + } else if (!(f = fopen(argv[optind], "rb"))) { + fprintf(stderr, "iconv: %s: ", argv[optind]); + perror(""); + err = 1; + continue; + } + inb = 0; + for (;;) { + in = buf; + out = outbuf; + l = fread(buf+inb, 1, sizeof(buf)-inb, f); + inb += l; + if (!inb) break; + if (iconv(cd, &in, &inb, &out, (size_t [1]){sizeof outbuf})==-1 + && errno == EILSEQ) { + if (!unitsize) { + wchar_t wc='0'; + char dummy[4], *dummyp=dummy; + iconv_t cd2 = iconv_open(from, "WCHAR_T"); + if (cd == (iconv_t)-1) { + unitsize = 1; + } else { + iconv(cd2, + (char *[1]){(char *)&wc}, + (size_t[1]){1}, + &dummyp, (size_t[1]){4}); + unitsize = dummyp-dummy; + if (!unitsize) unitsize=1; + } + } + inb-=unitsize; + in+=unitsize; + } + if (inb && !l && errno==EINVAL) break; + if (out>outbuf && !fwrite(outbuf, out-outbuf, 1, stdout)) { + perror("iconv: write error"); + exit(1); + } + if (inb) memmove(buf, in, inb); + } + if (ferror(f)) { + fprintf(stderr, "iconv: %s: ", argv[optind]); + perror(""); + err = 1; + } + } + return err; +} diff --git a/system/musl/ldconfig b/system/musl/ldconfig new file mode 100644 index 000000000..ccf7c2aa4 --- /dev/null +++ b/system/musl/ldconfig @@ -0,0 +1,18 @@ +#!/bin/sh +scan_dirs() { + scanelf -qS "$@" | while read SONAME FILE; do + TARGET="${FILE##*/}" + LINK="${FILE%/*}/$SONAME" + case "$FILE" in + /lib/*|/usr/lib/*|/usr/local/lib/*) ;; + *) [ -h "$LINK" -o ! -e "$LINK" ] && ln -sf "$TARGET" "$LINK" + esac + done + return 0 +} +# eat ldconfig options +while getopts "nNvXvf:C:r:" opt; do + : +done +shift $(( $OPTIND - 1 )) +[ $# -gt 0 ] && scan_dirs "$@" |