summaryrefslogtreecommitdiffstats
path: root/main/musl
diff options
context:
space:
mode:
authorTimo Teräs <timo.teras@iki.fi>2014-06-07 07:24:12 +0300
committerTimo Teräs <timo.teras@iki.fi>2014-06-07 07:24:12 +0300
commit838bcec8e10868ef80df1b638d5c8650a7260e7b (patch)
tree0b9ff8e7eaa7ecc1f05d2b3161b558c01e3c06e4 /main/musl
parentace7896296b96faa72fcb545501b6efba632f875 (diff)
downloadaports-838bcec8e10868ef80df1b638d5c8650a7260e7b.tar.bz2
aports-838bcec8e10868ef80df1b638d5c8650a7260e7b.tar.xz
main/musl: upgrade to 1.1.2
Diffstat (limited to 'main/musl')
-rw-r--r--main/musl/0001-v1.1.1-to-76f440cf.patch3459
-rw-r--r--main/musl/0002-76f440cf-to-d85d261e.patch89
-rw-r--r--main/musl/0003-d85d261e-to-2abb70c3.patch540
-rw-r--r--main/musl/1003-implement-y-and-C-specifiers-in-strptime.patch64
-rw-r--r--main/musl/APKBUILD26
5 files changed, 5 insertions, 4173 deletions
diff --git a/main/musl/0001-v1.1.1-to-76f440cf.patch b/main/musl/0001-v1.1.1-to-76f440cf.patch
deleted file mode 100644
index e4025585e..000000000
--- a/main/musl/0001-v1.1.1-to-76f440cf.patch
+++ /dev/null
@@ -1,3459 +0,0 @@
-diff --git a/arch/arm/bits/syscall.h b/arch/arm/bits/syscall.h
-index dc54bde..0b6ea7d 100644
---- a/arch/arm/bits/syscall.h
-+++ b/arch/arm/bits/syscall.h
-@@ -333,6 +333,8 @@
- #define __NR_process_vm_writev 377
- #define __NR_kcmp 378
- #define __NR_finit_module 379
-+#define __NR_sched_setattr 380
-+#define __NR_sched_getattr 381
-
-
- /* Repeated with SYS_ prefix */
-@@ -672,3 +674,5 @@
- #define SYS_process_vm_writev 377
- #define SYS_kcmp 378
- #define SYS_finit_module 379
-+#define SYS_sched_setattr 380
-+#define SYS_sched_getattr 381
-diff --git a/arch/i386/bits/syscall.h b/arch/i386/bits/syscall.h
-index 2af242b..7e48791 100644
---- a/arch/i386/bits/syscall.h
-+++ b/arch/i386/bits/syscall.h
-@@ -349,6 +349,8 @@
- #define __NR_process_vm_writev 348
- #define __NR_kcmp 349
- #define __NR_finit_module 350
-+#define __NR_sched_setattr 351
-+#define __NR_sched_getattr 352
-
-
- /* Repeated with SYS_ prefix */
-@@ -704,3 +706,5 @@
- #define SYS_process_vm_writev 348
- #define SYS_kcmp 349
- #define SYS_finit_module 350
-+#define SYS_sched_setattr 351
-+#define SYS_sched_getattr 352
-diff --git a/arch/microblaze/bits/syscall.h b/arch/microblaze/bits/syscall.h
-index 712d47a..b8b1d2e 100644
---- a/arch/microblaze/bits/syscall.h
-+++ b/arch/microblaze/bits/syscall.h
-@@ -375,6 +375,8 @@
- #define __NR_process_vm_writev 378
- #define __NR_kcmp 379
- #define __NR_finit_module 380
-+#define __NR_sched_setattr 381
-+#define __NR_sched_getattr 382
-
- /* Repeated with SYS_ prefix */
-
-@@ -756,3 +758,5 @@
- #define SYS_process_vm_writev 378
- #define SYS_kcmp 379
- #define SYS_finit_module 380
-+#define SYS_sched_setattr 381
-+#define SYS_sched_getattr 382
-diff --git a/arch/mips/bits/syscall.h b/arch/mips/bits/syscall.h
-index 574d603..f3d30d0 100644
---- a/arch/mips/bits/syscall.h
-+++ b/arch/mips/bits/syscall.h
-@@ -346,6 +346,8 @@
- #define __NR_process_vm_writev 4346
- #define __NR_kcmp 4347
- #define __NR_finit_module 4348
-+#define __NR_sched_setattr 4349
-+#define __NR_sched_getattr 4350
-
-
- /* Repeated with SYS_ prefix */
-@@ -697,3 +699,5 @@
- #define SYS_process_vm_writev 4346
- #define SYS_kcmp 4347
- #define SYS_finit_module 4348
-+#define SYS_sched_setattr 4349
-+#define SYS_sched_getattr 4350
-diff --git a/arch/mips/syscall_arch.h b/arch/mips/syscall_arch.h
-index c52976e..e62c339 100644
---- a/arch/mips/syscall_arch.h
-+++ b/arch/mips/syscall_arch.h
-@@ -5,6 +5,8 @@
-
- long (__syscall)(long, ...);
-
-+#define SYSCALL_RLIM_INFINITY (-1UL/2)
-+
- #ifndef __clang__
-
- #define __asm_syscall(...) do { \
-diff --git a/arch/powerpc/bits/syscall.h b/arch/powerpc/bits/syscall.h
-index 385860b..16f0abe 100644
---- a/arch/powerpc/bits/syscall.h
-+++ b/arch/powerpc/bits/syscall.h
-@@ -368,6 +368,8 @@
- #define __NR_process_vm_writev 352
- #define __NR_finit_module 353
- #define __NR_kcmp 354
-+#define __NR_sched_setattr 355
-+#define __NR_sched_getattr 356
-
- /*
- * repeated with SYS prefix
-@@ -742,3 +744,5 @@
- #define SYS_process_vm_writev 352
- #define SYS_finit_module 353
- #define SYS_kcmp 354
-+#define SYS_sched_setattr 355
-+#define SYS_sched_getattr 356
-diff --git a/arch/x32/bits/syscall.h b/arch/x32/bits/syscall.h
-index 95e2d2f..1c245e7 100644
---- a/arch/x32/bits/syscall.h
-+++ b/arch/x32/bits/syscall.h
-@@ -271,6 +271,9 @@
- #define __NR_getcpu (__X32_SYSCALL_BIT + 309)
- #define __NR_kcmp (__X32_SYSCALL_BIT + 312)
- #define __NR_finit_module (__X32_SYSCALL_BIT + 313)
-+#define __NR_sched_setattr (__X32_SYSCALL_BIT + 314)
-+#define __NR_sched_getattr (__X32_SYSCALL_BIT + 315)
-+
- #define __NR_rt_sigaction (__X32_SYSCALL_BIT + 512)
- #define __NR_rt_sigreturn (__X32_SYSCALL_BIT + 513)
- #define __NR_ioctl (__X32_SYSCALL_BIT + 514)
-@@ -591,6 +594,9 @@
- #define SYS_getcpu __NR_getcpu
- #define SYS_kcmp __NR_kcmp
- #define SYS_finit_module __NR_finit_module
-+#define SYS_sched_setattr __NR_sched_setattr
-+#define SYS_sched_getattr __NR_sched_getattr
-+
- #define SYS_rt_sigaction __NR_rt_sigaction
- #define SYS_rt_sigreturn __NR_rt_sigreturn
- #define SYS_ioctl __NR_ioctl
-diff --git a/arch/x86_64/bits/syscall.h b/arch/x86_64/bits/syscall.h
-index 5eb9b83..7bcb711 100644
---- a/arch/x86_64/bits/syscall.h
-+++ b/arch/x86_64/bits/syscall.h
-@@ -312,6 +312,8 @@
- #define __NR_process_vm_writev 311
- #define __NR_kcmp 312
- #define __NR_finit_module 313
-+#define __NR_sched_setattr 314
-+#define __NR_sched_getattr 315
-
- #undef __NR_fstatat
- #undef __NR_pread
-@@ -641,6 +643,8 @@
- #define SYS_process_vm_writev 311
- #define SYS_kcmp 312
- #define SYS_finit_module 313
-+#define SYS_sched_setattr 314
-+#define SYS_sched_getattr 315
-
- #undef SYS_fstatat
- #undef SYS_pread
-diff --git a/include/netinet/in.h b/include/netinet/in.h
-index ee6e19f..89188c7 100644
---- a/include/netinet/in.h
-+++ b/include/netinet/in.h
-@@ -198,6 +198,7 @@ uint16_t ntohs(uint16_t);
- #define IP_ORIGDSTADDR 20
- #define IP_RECVORIGDSTADDR IP_ORIGDSTADDR
- #define IP_MINTTL 21
-+#define IP_NODEFRAG 22
- #define IP_MULTICAST_IF 32
- #define IP_MULTICAST_TTL 33
- #define IP_MULTICAST_LOOP 34
-@@ -218,6 +219,7 @@ uint16_t ntohs(uint16_t);
- #define IP_PMTUDISC_DO 2
- #define IP_PMTUDISC_PROBE 3
- #define IP_PMTUDISC_INTERFACE 4
-+#define IP_PMTUDISC_OMIT 5
-
- #define IP_DEFAULT_MULTICAST_TTL 1
- #define IP_DEFAULT_MULTICAST_LOOP 1
-@@ -351,9 +353,17 @@ struct ip6_mtuinfo
- #define IPV6_RTHDR 57
- #define IPV6_RECVDSTOPTS 58
- #define IPV6_DSTOPTS 59
--
-+#define IPV6_RECVPATHMTU 60
-+#define IPV6_PATHMTU 61
-+#define IPV6_DONTFRAG 62
- #define IPV6_RECVTCLASS 66
- #define IPV6_TCLASS 67
-+#define IPV6_ADDR_PREFERENCES 72
-+#define IPV6_MINHOPCOUNT 73
-+#define IPV6_ORIGDSTADDR 74
-+#define IPV6_RECVORIGDSTADDR IPV6_ORIGDSTADDR
-+#define IPV6_TRANSPARENT 75
-+#define IPV6_UNICAST_IF 76
-
- #define IPV6_ADD_MEMBERSHIP IPV6_JOIN_GROUP
- #define IPV6_DROP_MEMBERSHIP IPV6_LEAVE_GROUP
-@@ -364,6 +374,16 @@ struct ip6_mtuinfo
- #define IPV6_PMTUDISC_WANT 1
- #define IPV6_PMTUDISC_DO 2
- #define IPV6_PMTUDISC_PROBE 3
-+#define IPV6_PMTUDISC_INTERFACE 4
-+#define IPV6_PMTUDISC_OMIT 5
-+
-+#define IPV6_PREFER_SRC_TMP 0x0001
-+#define IPV6_PREFER_SRC_PUBLIC 0x0002
-+#define IPV6_PREFER_SRC_PUBTMP_DEFAULT 0x0100
-+#define IPV6_PREFER_SRC_COA 0x0004
-+#define IPV6_PREFER_SRC_HOME 0x0400
-+#define IPV6_PREFER_SRC_CGA 0x0008
-+#define IPV6_PREFER_SRC_NONCGA 0x0800
-
- #define IPV6_RTHDR_LOOSE 0
- #define IPV6_RTHDR_STRICT 1
-diff --git a/include/sched.h b/include/sched.h
-index 105dac9..4394b64 100644
---- a/include/sched.h
-+++ b/include/sched.h
-@@ -38,6 +38,7 @@ int sched_yield(void);
- #define SCHED_RR 2
- #define SCHED_BATCH 3
- #define SCHED_IDLE 5
-+#define SCHED_DEADLINE 6
- #define SCHED_RESET_ON_FORK 0x40000000
-
- #ifdef _GNU_SOURCE
-diff --git a/include/signal.h b/include/signal.h
-index 3fb21b2..c36e4d5 100644
---- a/include/signal.h
-+++ b/include/signal.h
-@@ -89,19 +89,24 @@ typedef struct {
- union {
- char __pad[128 - 2*sizeof(int) - sizeof(long)];
- struct {
-- pid_t si_pid;
-- uid_t si_uid;
-- union sigval si_sigval;
-- } __rt;
-- struct {
-- unsigned int si_timer1, si_timer2;
-- } __timer;
-- struct {
-- pid_t si_pid;
-- uid_t si_uid;
-- int si_status;
-- clock_t si_utime, si_stime;
-- } __sigchld;
-+ union {
-+ struct {
-+ pid_t si_pid;
-+ uid_t si_uid;
-+ } __piduid;
-+ struct {
-+ int si_timerid;
-+ int si_overrun;
-+ } __timer;
-+ } __first;
-+ union {
-+ union sigval si_value;
-+ struct {
-+ int si_status;
-+ clock_t si_utime, si_stime;
-+ } __sigchld;
-+ } __second;
-+ } __si_common;
- struct {
- void *si_addr;
- short si_addr_lsb;
-@@ -117,20 +122,20 @@ typedef struct {
- } __sigsys;
- } __si_fields;
- } siginfo_t;
--#define si_pid __si_fields.__sigchld.si_pid
--#define si_uid __si_fields.__sigchld.si_uid
--#define si_status __si_fields.__sigchld.si_status
--#define si_utime __si_fields.__sigchld.si_utime
--#define si_stime __si_fields.__sigchld.si_stime
--#define si_value __si_fields.__rt.si_sigval
-+#define si_pid __si_fields.__si_common.__first.__piduid.si_pid
-+#define si_uid __si_fields.__si_common.__first.__piduid.si_uid
-+#define si_status __si_fields.__si_common.__second.__sigchld.si_status
-+#define si_utime __si_fields.__si_common.__second.__sigchld.si_utime
-+#define si_stime __si_fields.__si_common.__second.__sigchld.si_stime
-+#define si_value __si_fields.__si_common.__second.si_value
- #define si_addr __si_fields.__sigfault.si_addr
- #define si_addr_lsb __si_fields.__sigfault.si_addr_lsb
- #define si_band __si_fields.__sigpoll.si_band
- #define si_fd __si_fields.__sigpoll.si_fd
--#define si_timer1 __si_fields.__timer.si_timer1
--#define si_timer2 __si_fields.__timer.si_timer2
--#define si_ptr __si_fields.__rt.si_sigval.sival_ptr
--#define si_int __si_fields.__rt.si_sigval.sival_int
-+#define si_timerid __si_fields.__si_common.__first.__timer.si_timerid
-+#define si_overrun __si_fields.__si_common.__first.__timer.si_overrun
-+#define si_ptr si_value.sival_ptr
-+#define si_int si_value.sival_int
- #define si_call_addr __si_fields.__sigsys.si_call_addr
- #define si_syscall __si_fields.__sigsys.si_syscall
- #define si_arch __si_fields.__sigsys.si_arch
-diff --git a/include/sys/socket.h b/include/sys/socket.h
-index 8e8c9e9..d752791 100644
---- a/include/sys/socket.h
-+++ b/include/sys/socket.h
-@@ -203,6 +203,7 @@ struct linger
- #define SO_SELECT_ERR_QUEUE 45
- #define SO_BUSY_POLL 46
- #define SO_MAX_PACING_RATE 47
-+#define SO_BPF_EXTENSIONS 48
-
- #ifndef SOL_SOCKET
- #define SOL_SOCKET 1
-diff --git a/include/sys/types.h b/include/sys/types.h
-index 27170f6..f00db03 100644
---- a/include/sys/types.h
-+++ b/include/sys/types.h
-@@ -20,11 +20,6 @@ extern "C" {
- #define __NEED_timer_t
- #define __NEED_clockid_t
-
--#define __NEED_int8_t
--#define __NEED_int16_t
--#define __NEED_int32_t
--#define __NEED_int64_t
--
- #define __NEED_blkcnt_t
- #define __NEED_fsblkcnt_t
- #define __NEED_fsfilcnt_t
-@@ -49,19 +44,22 @@ extern "C" {
- #define __NEED_pthread_key_t
- #define __NEED_pthread_once_t
- #define __NEED_useconds_t
--#define __NEED_u_int64_t
-
- #if defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
-+#define __NEED_int8_t
-+#define __NEED_int16_t
-+#define __NEED_int32_t
-+#define __NEED_int64_t
-+#define __NEED_u_int64_t
- #define __NEED_register_t
- #endif
-
- #include <bits/alltypes.h>
-
-+#if defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
- typedef unsigned char u_int8_t;
- typedef unsigned short u_int16_t;
- typedef unsigned u_int32_t;
--
--#if defined(_GNU_SOURCE) || defined(_BSD_SOURCE)
- typedef char *caddr_t;
- typedef unsigned char u_char;
- typedef unsigned short u_short, ushort;
-@@ -87,5 +85,3 @@ typedef unsigned long long u_quad_t;
- }
- #endif
- #endif
--
--
-diff --git a/src/env/__libc_start_main.c b/src/env/__libc_start_main.c
-index 3498afb..c10a3f3 100644
---- a/src/env/__libc_start_main.c
-+++ b/src/env/__libc_start_main.c
-@@ -1,6 +1,7 @@
- #include <elf.h>
- #include <poll.h>
- #include <fcntl.h>
-+#include <signal.h>
- #include "syscall.h"
- #include "atomic.h"
- #include "libc.h"
-@@ -48,9 +49,13 @@ void __init_libc(char **envp, char *pn)
- && !aux[AT_SECURE]) return;
-
- struct pollfd pfd[3] = { {.fd=0}, {.fd=1}, {.fd=2} };
-+#ifdef SYS_poll
- __syscall(SYS_poll, pfd, 3, 0);
-+#else
-+ __syscall(SYS_ppoll, pfd, 3, &(struct timespec){0}, 0, _NSIG/8);
-+#endif
- for (i=0; i<3; i++) if (pfd[i].revents&POLLNVAL)
-- if (__syscall(SYS_open, "/dev/null", O_RDWR|O_LARGEFILE)<0)
-+ if (__sys_open("/dev/null", O_RDWR)<0)
- a_crash();
- libc.secure = 1;
- }
-diff --git a/src/exit/exit.c b/src/exit/exit.c
-index 353f50b..695bdc0 100644
---- a/src/exit/exit.c
-+++ b/src/exit/exit.c
-@@ -1,8 +1,6 @@
- #include <stdlib.h>
- #include <stdint.h>
- #include "libc.h"
--#include "atomic.h"
--#include "syscall.h"
-
- static void dummy()
- {
-@@ -21,11 +19,6 @@ extern void (*const __fini_array_end)() __attribute__((weak));
-
- _Noreturn void exit(int code)
- {
-- static int lock;
--
-- /* If more than one thread calls exit, hang until _Exit ends it all */
-- while (a_swap(&lock, 1)) __syscall(SYS_pause);
--
- __funcs_on_exit();
-
- #ifndef SHARED
-diff --git a/src/exit/quick_exit.c b/src/exit/quick_exit.c
-index 1175d80..ada9134 100644
---- a/src/exit/quick_exit.c
-+++ b/src/exit/quick_exit.c
-@@ -1,6 +1,4 @@
- #include <stdlib.h>
--#include "syscall.h"
--#include "atomic.h"
- #include "libc.h"
-
- static void dummy() { }
-@@ -8,8 +6,6 @@ weak_alias(dummy, __funcs_on_quick_exit);
-
- _Noreturn void quick_exit(int code)
- {
-- static int lock;
-- while (a_swap(&lock, 1)) __syscall(SYS_pause);
- __funcs_on_quick_exit();
- _Exit(code);
- }
-diff --git a/src/fcntl/open.c b/src/fcntl/open.c
-index be44208..0594ed7 100644
---- a/src/fcntl/open.c
-+++ b/src/fcntl/open.c
-@@ -10,7 +10,7 @@ int open(const char *filename, int flags, ...)
- va_start(ap, flags);
- mode = va_arg(ap, mode_t);
- va_end(ap);
-- return syscall_cp(SYS_open, filename, flags|O_LARGEFILE, mode);
-+ return sys_open_cp(filename, flags, mode);
- }
-
- LFS64(open);
-diff --git a/src/internal/syscall.h b/src/internal/syscall.h
-index 914b0d1..0a2840a 100644
---- a/src/internal/syscall.h
-+++ b/src/internal/syscall.h
-@@ -4,6 +4,10 @@
- #include <sys/syscall.h>
- #include "syscall_arch.h"
-
-+#ifndef SYSCALL_RLIM_INFINITY
-+#define SYSCALL_RLIM_INFINITY (~0ULL)
-+#endif
-+
- #ifndef __scc
- #define __scc(X) ((long) (X))
- typedef long syscall_arg_t;
-@@ -122,14 +126,26 @@ long __syscall_ret(unsigned long), __syscall(syscall_arg_t, ...),
-
- #ifdef SYS_stat64
- #undef SYS_stat
--#undef SYS_fstat
--#undef SYS_lstat
--#undef SYS_statfs
--#undef SYS_fstatfs
- #define SYS_stat SYS_stat64
-+#endif
-+
-+#ifdef SYS_fstat64
-+#undef SYS_fstat
- #define SYS_fstat SYS_fstat64
-+#endif
-+
-+#ifdef SYS_lstat64
-+#undef SYS_lstat
- #define SYS_lstat SYS_lstat64
-+#endif
-+
-+#ifdef SYS_statfs64
-+#undef SYS_statfs
- #define SYS_statfs SYS_statfs64
-+#endif
-+
-+#ifdef SYS_fstatfs64
-+#undef SYS_fstatfs
- #define SYS_fstatfs SYS_fstatfs64
- #endif
-
-@@ -163,6 +179,9 @@ long __syscall_ret(unsigned long), __syscall(syscall_arg_t, ...),
- #define SYS_fadvise SYS_fadvise64_64
- #endif
-
-+#ifdef SYS_sendfile64
-+#undef SYS_sendfile
-+#define SYS_sendfile SYS_sendfile64
- #endif
-
- /* socketcall calls */
-@@ -187,3 +206,23 @@ long __syscall_ret(unsigned long), __syscall(syscall_arg_t, ...),
- #define __SC_accept4 18
- #define __SC_recvmmsg 19
- #define __SC_sendmmsg 20
-+
-+#ifdef SYS_open
-+#define __sys_open2(x,pn,fl) __syscall2(SYS_open, pn, (fl)|O_LARGEFILE)
-+#define __sys_open3(x,pn,fl,mo) __syscall3(SYS_open, pn, (fl)|O_LARGEFILE, mo)
-+#define __sys_open_cp2(x,pn,fl) __syscall_cp2(SYS_open, pn, (fl)|O_LARGEFILE)
-+#define __sys_open_cp3(x,pn,fl,mo) __syscall_cp3(SYS_open, pn, (fl)|O_LARGEFILE, mo)
-+#else
-+#define __sys_open2(x,pn,fl) __syscall3(SYS_openat, AT_FDCWD, pn, (fl)|O_LARGEFILE)
-+#define __sys_open3(x,pn,fl,mo) __syscall4(SYS_openat, AT_FDCWD, pn, (fl)|O_LARGEFILE, mo)
-+#define __sys_open_cp2(x,pn,fl) __syscall_cp3(SYS_openat, AT_FDCWD, pn, (fl)|O_LARGEFILE)
-+#define __sys_open_cp3(x,pn,fl,mo) __syscall_cp4(SYS_openat, AT_FDCWD, pn, (fl)|O_LARGEFILE, mo)
-+#endif
-+
-+#define __sys_open(...) __SYSCALL_DISP(__sys_open,,__VA_ARGS__)
-+#define sys_open(...) __syscall_ret(__sys_open(__VA_ARGS__))
-+
-+#define __sys_open_cp(...) __SYSCALL_DISP(__sys_open_cp,,__VA_ARGS__)
-+#define sys_open_cp(...) __syscall_ret(__sys_open_cp(__VA_ARGS__))
-+
-+#endif
-diff --git a/src/linux/epoll.c b/src/linux/epoll.c
-index 030786d..deff5b1 100644
---- a/src/linux/epoll.c
-+++ b/src/linux/epoll.c
-@@ -1,15 +1,20 @@
- #include <sys/epoll.h>
- #include <signal.h>
-+#include <errno.h>
- #include "syscall.h"
-
- int epoll_create(int size)
- {
-- return syscall(SYS_epoll_create, size);
-+ return epoll_create1(0);
- }
-
- int epoll_create1(int flags)
- {
-- return syscall(SYS_epoll_create1, flags);
-+ int r = __syscall(SYS_epoll_create1, flags);
-+#ifdef SYS_epoll_create
-+ if (r==-ENOSYS && !flags) r = __syscall(SYS_epoll_create, 1);
-+#endif
-+ return __syscall_ret(r);
- }
-
- int epoll_ctl(int fd, int op, int fd2, struct epoll_event *ev)
-@@ -19,10 +24,14 @@ int epoll_ctl(int fd, int op, int fd2, struct epoll_event *ev)
-
- int epoll_pwait(int fd, struct epoll_event *ev, int cnt, int to, const sigset_t *sigs)
- {
-- return syscall(SYS_epoll_pwait, fd, ev, cnt, to, sigs, _NSIG/8);
-+ int r = __syscall(SYS_epoll_pwait, fd, ev, cnt, to, sigs, _NSIG/8);
-+#ifdef SYS_epoll_wait
-+ if (r==-ENOSYS && !sigs) r = __syscall(SYS_epoll_wait, fd, ev, cnt, to);
-+#endif
-+ return __syscall_ret(r);
- }
-
- int epoll_wait(int fd, struct epoll_event *ev, int cnt, int to)
- {
-- return syscall(SYS_epoll_wait, fd, ev, cnt, to);
-+ return epoll_pwait(fd, ev, cnt, to, 0);
- }
-diff --git a/src/linux/eventfd.c b/src/linux/eventfd.c
-index 5306648..68e489c 100644
---- a/src/linux/eventfd.c
-+++ b/src/linux/eventfd.c
-@@ -1,10 +1,15 @@
- #include <sys/eventfd.h>
- #include <unistd.h>
-+#include <errno.h>
- #include "syscall.h"
-
- int eventfd(unsigned int count, int flags)
- {
-- return syscall(flags ? SYS_eventfd2 : SYS_eventfd, count, flags);
-+ int r = __syscall(SYS_eventfd2, count, flags);
-+#ifdef SYS_eventfd
-+ if (r==-ENOSYS && !flags) r = __syscall(SYS_eventfd, count);
-+#endif
-+ return __syscall_ret(r);
- }
-
- int eventfd_read(int fd, eventfd_t *value)
-diff --git a/src/linux/inotify.c b/src/linux/inotify.c
-index a417c89..df5e48b 100644
---- a/src/linux/inotify.c
-+++ b/src/linux/inotify.c
-@@ -1,13 +1,18 @@
- #include <sys/inotify.h>
-+#include <errno.h>
- #include "syscall.h"
-
- int inotify_init()
- {
-- return syscall(SYS_inotify_init);
-+ return inotify_init1(0);
- }
- int inotify_init1(int flags)
- {
-- return syscall(SYS_inotify_init1, flags);
-+ int r = __syscall(SYS_inotify_init1, flags);
-+#ifdef SYS_inotify_init
-+ if (r==-ENOSYS && !flags) r = __syscall(SYS_inotify_init);
-+#endif
-+ return __syscall_ret(r);
- }
-
- int inotify_add_watch(int fd, const char *pathname, uint32_t mask)
-diff --git a/src/linux/prlimit.c b/src/linux/prlimit.c
-index d1639cc..0fe28e1 100644
---- a/src/linux/prlimit.c
-+++ b/src/linux/prlimit.c
-@@ -3,9 +3,24 @@
- #include "syscall.h"
- #include "libc.h"
-
-+#define FIX(x) do{ if ((x)>=SYSCALL_RLIM_INFINITY) (x)=RLIM_INFINITY; }while(0)
-+
- int prlimit(pid_t pid, int resource, const struct rlimit *new_limit, struct rlimit *old_limit)
- {
-- return syscall(SYS_prlimit64, pid, resource, new_limit, old_limit);
-+ struct rlimit tmp;
-+ int r;
-+ if (new_limit && SYSCALL_RLIM_INFINITY != RLIM_INFINITY) {
-+ tmp = *new_limit;
-+ FIX(tmp.rlim_cur);
-+ FIX(tmp.rlim_max);
-+ new_limit = &tmp;
-+ }
-+ r = syscall(SYS_prlimit64, pid, resource, new_limit, old_limit);
-+ if (!r && old_limit && SYSCALL_RLIM_INFINITY != RLIM_INFINITY) {
-+ FIX(old_limit->rlim_cur);
-+ FIX(old_limit->rlim_max);
-+ }
-+ return r;
- }
-
- #undef prlimit64
-diff --git a/src/linux/signalfd.c b/src/linux/signalfd.c
-index da6bced..4bf4332 100644
---- a/src/linux/signalfd.c
-+++ b/src/linux/signalfd.c
-@@ -7,6 +7,7 @@
- int signalfd(int fd, const sigset_t *sigs, int flags)
- {
- int ret = __syscall(SYS_signalfd4, fd, sigs, _NSIG/8, flags);
-+#ifdef SYS_signalfd
- if (ret != -ENOSYS) return __syscall_ret(ret);
- ret = __syscall(SYS_signalfd, fd, sigs, _NSIG/8);
- if (ret >= 0) {
-@@ -15,5 +16,6 @@ int signalfd(int fd, const sigset_t *sigs, int flags)
- if (flags & SFD_NONBLOCK)
- __syscall(SYS_fcntl, ret, F_SETFL, O_NONBLOCK);
- }
-+#endif
- return __syscall_ret(ret);
- }
-diff --git a/src/linux/utimes.c b/src/linux/utimes.c
-index 70c0695..b814c88 100644
---- a/src/linux/utimes.c
-+++ b/src/linux/utimes.c
-@@ -1,7 +1,10 @@
- #include <sys/time.h>
-+#include "fcntl.h"
- #include "syscall.h"
-
-+int __futimesat(int, const char *, const struct timeval [2]);
-+
- int utimes(const char *path, const struct timeval times[2])
- {
-- return syscall(SYS_utimes, path, times);
-+ return __futimesat(AT_FDCWD, path, times);
- }
-diff --git a/src/misc/getrlimit.c b/src/misc/getrlimit.c
-index b7bbd06..b073677 100644
---- a/src/misc/getrlimit.c
-+++ b/src/misc/getrlimit.c
-@@ -3,16 +3,24 @@
- #include "syscall.h"
- #include "libc.h"
-
-+#define FIX(x) do{ if ((x)>=SYSCALL_RLIM_INFINITY) (x)=RLIM_INFINITY; }while(0)
-+
- int getrlimit(int resource, struct rlimit *rlim)
- {
- unsigned long k_rlim[2];
- int ret = syscall(SYS_prlimit64, 0, resource, 0, rlim);
-+ if (!ret) {
-+ FIX(rlim->rlim_cur);
-+ FIX(rlim->rlim_max);
-+ }
- if (!ret || errno != ENOSYS)
- return ret;
- if (syscall(SYS_getrlimit, resource, k_rlim) < 0)
- return -1;
- rlim->rlim_cur = k_rlim[0] == -1UL ? RLIM_INFINITY : k_rlim[0];
- rlim->rlim_max = k_rlim[1] == -1UL ? RLIM_INFINITY : k_rlim[1];
-+ FIX(rlim->rlim_cur);
-+ FIX(rlim->rlim_max);
- return 0;
- }
-
-diff --git a/src/misc/realpath.c b/src/misc/realpath.c
-index 4cc7e7d..88c849c 100644
---- a/src/misc/realpath.c
-+++ b/src/misc/realpath.c
-@@ -22,7 +22,7 @@ char *realpath(const char *restrict filename, char *restrict resolved)
- return 0;
- }
-
-- fd = syscall(SYS_open, filename, O_PATH|O_NONBLOCK|O_CLOEXEC|O_LARGEFILE);
-+ fd = sys_open(filename, O_PATH|O_NONBLOCK|O_CLOEXEC);
- if (fd < 0) return 0;
- __procfdname(buf, fd);
-
-diff --git a/src/misc/setrlimit.c b/src/misc/setrlimit.c
-index ddc13e9..8a1b8cc 100644
---- a/src/misc/setrlimit.c
-+++ b/src/misc/setrlimit.c
-@@ -4,14 +4,22 @@
- #include "libc.h"
-
- #define MIN(a, b) ((a)<(b) ? (a) : (b))
-+#define FIX(x) do{ if ((x)>=SYSCALL_RLIM_INFINITY) (x)=RLIM_INFINITY; }while(0)
-
- int __setrlimit(int resource, const struct rlimit *rlim)
- {
- unsigned long k_rlim[2];
-+ struct rlimit tmp;
-+ if (SYSCALL_RLIM_INFINITY != RLIM_INFINITY) {
-+ tmp = *rlim;
-+ FIX(tmp.rlim_cur);
-+ FIX(tmp.rlim_max);
-+ rlim = &tmp;
-+ }
- int ret = __syscall(SYS_prlimit64, 0, resource, rlim, 0);
- if (ret != -ENOSYS) return ret;
-- k_rlim[0] = MIN(rlim->rlim_cur, -1UL);
-- k_rlim[1] = MIN(rlim->rlim_max, -1UL);
-+ k_rlim[0] = MIN(rlim->rlim_cur, MIN(-1UL, SYSCALL_RLIM_INFINITY));
-+ k_rlim[1] = MIN(rlim->rlim_max, MIN(-1UL, SYSCALL_RLIM_INFINITY));
- return __syscall(SYS_setrlimit, resource, k_rlim);
- }
-
-diff --git a/src/network/__dns.c b/src/network/__dns.c
-deleted file mode 100644
-index 97d8031..0000000
---- a/src/network/__dns.c
-+++ /dev/null
-@@ -1,282 +0,0 @@
--#include <stdint.h>
--#include <netdb.h>
--#include <stdio.h>
--#include <fcntl.h>
--#include <limits.h>
--#include <string.h>
--#include <sys/socket.h>
--#include <poll.h>
--#include <netinet/in.h>
--#include <time.h>
--#include <ctype.h>
--#include <unistd.h>
--#include <pthread.h>
--#include <errno.h>
--#include "__dns.h"
--#include "stdio_impl.h"
--
--#define TIMEOUT 5
--#define RETRY 1000
--#define PACKET_MAX 512
--#define PTR_MAX (64 + sizeof ".in-addr.arpa")
--
--static void cleanup(void *p)
--{
-- close((intptr_t)p);
--}
--
--int __dns_doqueries(unsigned char *dest, const char *name, int *rr, int rrcnt)
--{
-- time_t t0 = time(0);
-- int fd;
-- FILE *f, _f;
-- unsigned char _buf[256];
-- char line[64], *s, *z;
-- union {
-- struct sockaddr_in sin;
-- struct sockaddr_in6 sin6;
-- } sa = {0}, ns[3] = {{0}};
-- socklen_t sl = sizeof sa.sin;
-- int nns = 0;
-- int family = AF_INET;
-- unsigned char q[280] = "", *r = dest;
-- int ql;
-- int rlen;
-- int got = 0, failed = 0;
-- int errcode = EAI_AGAIN;
-- int i, j;
-- struct timespec ts;
-- struct pollfd pfd;
-- int id;
-- int cs;
--
-- pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs);
--
-- /* Construct query template - RR and ID will be filled later */
-- if (strlen(name)-1 >= 254U) return EAI_NONAME;
-- q[2] = q[5] = 1;
-- strcpy((char *)q+13, name);
-- for (i=13; q[i]; i=j+1) {
-- for (j=i; q[j] && q[j] != '.'; j++);
-- if (j-i-1u > 62u) return EAI_NONAME;
-- q[i-1] = j-i;
-- }
-- q[i+3] = 1;
-- ql = i+4;
--
-- /* Make a reasonably unpredictable id */
-- clock_gettime(CLOCK_REALTIME, &ts);
-- id = ts.tv_nsec + ts.tv_nsec/65536UL & 0xffff;
--
-- /* Get nameservers from resolv.conf, fallback to localhost */
-- f = __fopen_rb_ca("/etc/resolv.conf", &_f, _buf, sizeof _buf);
-- if (f) for (nns=0; nns<3 && fgets(line, sizeof line, f); ) {
-- if (strncmp(line, "nameserver", 10) || !isspace(line[10]))
-- continue;
-- for (s=line+11; isspace(*s); s++);
-- for (z=s; *z && !isspace(*z); z++);
-- *z=0;
-- if (__ipparse(ns+nns, AF_UNSPEC, s) < 0) continue;
-- ns[nns].sin.sin_port = htons(53);
-- if (ns[nns++].sin.sin_family == AF_INET6) {
-- family = AF_INET6;
-- sl = sizeof sa.sin6;
-- }
-- }
-- if (f) __fclose_ca(f);
-- if (!nns) {
-- ns[0].sin.sin_family = family = AF_INET;
-- ns[0].sin.sin_port = htons(53);
-- ns[0].sin.sin_addr.s_addr = htonl(0x7f000001);
-- nns=1;
-- sl = sizeof sa.sin;
-- }
--
-- /* Get local address and open/bind a socket */
-- sa.sin.sin_family = family;
-- fd = socket(family, SOCK_DGRAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0);
--
-- /* Handle case where system lacks IPv6 support */
-- if (fd < 0 && errno == EAFNOSUPPORT) {
-- if (family != AF_INET6) return EAI_SYSTEM;
-- fd = socket(AF_INET, SOCK_DGRAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0);
-- family = AF_INET;
-- }
-- if (fd < 0) return EAI_SYSTEM;
--
-- /* Convert any IPv4 addresses in a mixed environment to v4-mapped */
-- if (family == AF_INET6) {
-- setsockopt(fd, IPPROTO_IPV6, IPV6_V6ONLY, &(int){0}, sizeof 0);
-- for (i=0; i<nns; i++) {
-- if (ns[i].sin.sin_family != AF_INET) continue;
-- memcpy(ns[i].sin6.sin6_addr.s6_addr+12,
-- &ns[i].sin.sin_addr, 4);
-- memcpy(ns[i].sin6.sin6_addr.s6_addr,
-- "\0\0\0\0\0\0\0\0\0\0\xff\xff", 12);
-- ns[i].sin6.sin6_family = AF_INET6;
-- ns[i].sin6.sin6_flowinfo = 0;
-- ns[i].sin6.sin6_scope_id = 0;
-- }
-- }
--
-- pthread_cleanup_push(cleanup, (void *)(intptr_t)fd);
-- pthread_setcancelstate(cs, 0);
--
-- if (bind(fd, (void *)&sa, sl) < 0) {
-- errcode = EAI_SYSTEM;
-- goto out;
-- }
--
-- pfd.fd = fd;
-- pfd.events = POLLIN;
--
-- /* Loop until we timeout; break early on success */
-- for (; time(0)-t0 < TIMEOUT; ) {
--
-- /* Query all configured namservers in parallel */
-- for (i=0; i<rrcnt; i++) if (rr[i]) for (j=0; j<nns; j++) {
-- q[0] = id+i >> 8;
-- q[1] = id+i;
-- q[ql-3] = rr[i];
-- sendto(fd, q, ql, MSG_NOSIGNAL, (void *)&ns[j], sl);
-- }
--
-- /* Wait for a response, or until time to retry */
-- if (poll(&pfd, 1, RETRY) <= 0) continue;
--
-- /* Process any and all replies */
-- while (got+failed < rrcnt && (rlen = recvfrom(fd, r, 512, 0,
-- (void *)&sa, (socklen_t[1]){sl})) >= 2)
-- {
-- /* Ignore replies from addresses we didn't send to */
-- for (i=0; i<nns; i++) if (!memcmp(ns+i, &sa, sl)) break;
-- if (i==nns) continue;
--
-- /* Compute index of the query from id */
-- i = r[0]*256+r[1] - id & 0xffff;
-- if ((unsigned)i >= rrcnt || !rr[i]) continue;
--
-- /* Interpret the result code */
-- switch (r[3] & 15) {
-- case 0:
-- got++;
-- break;
-- case 3:
-- if (1) errcode = EAI_NONAME; else
-- default:
-- errcode = EAI_FAIL;
-- failed++;
-- }
--
-- /* Mark this record as answered */
-- rr[i] = 0;
-- r += 512;
-- }
--
-- /* Check to see if we have answers to all queries */
-- if (got+failed == rrcnt) break;
-- }
--out:
-- pthread_cleanup_pop(1);
--
-- /* Return the number of results, or an error code if none */
-- if (got) return got;
-- return errcode;
--}
--
--static void mkptr4(char *s, const unsigned char *ip)
--{
-- sprintf(s, "%d.%d.%d.%d.in-addr.arpa",
-- ip[3], ip[2], ip[1], ip[0]);
--}
--
--static void mkptr6(char *s, const unsigned char *ip)
--{
-- static const char xdigits[] = "0123456789abcdef";
-- int i;
-- for (i=15; i>=0; i--) {
-- *s++ = xdigits[ip[i]&15]; *s++ = '.';
-- *s++ = xdigits[ip[i]>>4]; *s++ = '.';
-- }
-- strcpy(s, "ip6.arpa");
--}
--
--int __dns_query(unsigned char *r, const void *a, int family, int ptr)
--{
-- char buf[PTR_MAX];
-- int rr[2], rrcnt = 1;
--
-- if (ptr) {
-- if (family == AF_INET6) mkptr6(buf, a);
-- else mkptr4(buf, a);
-- rr[0] = RR_PTR;
-- a = buf;
-- } else if (family == AF_INET6) {
-- rr[0] = RR_AAAA;
-- } else {
-- rr[0] = RR_A;
-- if (family != AF_INET) rr[rrcnt++] = RR_AAAA;
-- }
--
-- return __dns_doqueries(r, a, rr, rrcnt);
--}
--
--int __dn_expand(const unsigned char *, const unsigned char *, const unsigned char *, char *, int);
--
--int __dns_get_rr(void *dest, size_t stride, size_t maxlen, size_t limit, const unsigned char *r, int rr, int dec)
--{
-- int qdcount, ancount;
-- const unsigned char *p;
-- char tmp[256];
-- int found = 0;
-- int len;
--
-- if ((r[3]&15)) return 0;
-- p = r+12;
-- qdcount = r[4]*256 + r[5];
-- ancount = r[6]*256 + r[7];
-- if (qdcount+ancount > 64) return -1;
-- while (qdcount--) {
-- while (p-r < 512 && *p-1U < 127) p++;
-- if (*p>193 || (*p==193 && p[1]>254) || p>r+506)
-- return -1;
-- p += 5 + !!*p;
-- }
-- while (ancount--) {
-- while (p-r < 512 && *p-1U < 127) p++;
-- if (*p>193 || (*p==193 && p[1]>254) || p>r+506)
-- return -1;
-- p += 1 + !!*p;
-- len = p[8]*256 + p[9];
-- if (p+len > r+512) return -1;
-- if (p[1]==rr && len <= maxlen) {
-- if (dec && __dn_expand(r, r+512, p+10, tmp, sizeof tmp)<0)
-- return -1;
-- if (dest && limit) {
-- if (dec) strcpy(dest, tmp);
-- else memcpy(dest, p+10, len);
-- dest = (char *)dest + stride;
-- limit--;
-- }
-- found++;
-- }
-- p += 10 + len;
-- }
-- return found;
--}
--
--int __dns_count_addrs(const unsigned char *r, int cnt)
--{
-- int found=0, res, i;
-- static const int p[2][2] = { { 4, RR_A }, { 16, RR_AAAA } };
--
-- while (cnt--) {
-- for (i=0; i<2; i++) {
-- res = __dns_get_rr(0, 0, p[i][0], -1, r, p[i][1], 0);
-- if (res < 0) return res;
-- found += res;
-- }
-- r += 512;
-- }
-- return found;
--}
-diff --git a/src/network/__dns.h b/src/network/__dns.h
-deleted file mode 100644
-index 9a3f740..0000000
---- a/src/network/__dns.h
-+++ /dev/null
-@@ -1,14 +0,0 @@
--#include <stddef.h>
--
--#define RR_A 1
--#define RR_CNAME 5
--#define RR_PTR 12
--#define RR_AAAA 28
--
--int __dns_count_addrs(const unsigned char *, int);
--int __dns_get_rr(void *, size_t, size_t, size_t, const unsigned char *, int, int);
--
--int __dns_query(unsigned char *, const void *, int, int);
--int __ipparse(void *, int, const char *);
--
--int __dns_doqueries(unsigned char *, const char *, int *, int);
-diff --git a/src/network/__ipparse.c b/src/network/__ipparse.c
-deleted file mode 100644
-index 79f3b8c..0000000
---- a/src/network/__ipparse.c
-+++ /dev/null
-@@ -1,51 +0,0 @@
--#include <stdlib.h>
--#include <ctype.h>
--#include <sys/socket.h>
--#include <netinet/in.h>
--#include <arpa/inet.h>
--#include "__dns.h"
--
--int __ipparse(void *dest, int family, const char *s0)
--{
-- const char *s = s0;
-- unsigned char *d = dest;
-- unsigned long a[16] = { 0 };
-- char *z;
-- int i;
--
-- if (family == AF_INET6) goto not_v4;
--
-- for (i=0; i<4; i++) {
-- a[i] = strtoul(s, &z, 0);
-- if (z==s || (*z && *z != '.') || !isdigit(*s)) {
-- if (family == AF_INET) return -1;
-- goto not_v4;
-- }
-- if (!*z) break;
-- s=z+1;
-- }
-- if (i==4) return -1;
-- switch (i) {
-- case 0:
-- a[1] = a[0] & 0xffffff;
-- a[0] >>= 24;
-- case 1:
-- a[2] = a[1] & 0xffff;
-- a[1] >>= 16;
-- case 2:
-- a[3] = a[2] & 0xff;
-- a[2] >>= 8;
-- }
-- ((struct sockaddr_in *)d)->sin_family = AF_INET;
-- d = (void *)&((struct sockaddr_in *)d)->sin_addr;
-- for (i=0; i<4; i++) {
-- if (a[i] > 255) return -1;
-- d[i] = a[i];
-- }
-- return 0;
--
--not_v4:
-- s = s0;
-- ((struct sockaddr_in6 *)d)->sin6_family = AF_INET6;
-- return inet_pton(AF_INET6, s, (void *)&((struct sockaddr_in6 *)d)->sin6_addr) <= 0 ? -1 : 0;
--}
-diff --git a/src/network/dns_parse.c b/src/network/dns_parse.c
-new file mode 100644
-index 0000000..aa0d39f
---- /dev/null
-+++ b/src/network/dns_parse.c
-@@ -0,0 +1,31 @@
-+#include <string.h>
-+
-+int __dns_parse(const unsigned char *r, int rlen, int (*callback)(void *, int, const void *, int, const void *), void *ctx)
-+{
-+ int qdcount, ancount;
-+ const unsigned char *p;
-+ int len;
-+
-+ if ((r[3]&15)) return 0;
-+ p = r+12;
-+ qdcount = r[4]*256 + r[5];
-+ ancount = r[6]*256 + r[7];
-+ if (qdcount+ancount > 64) return -1;
-+ while (qdcount--) {
-+ while (p-r < rlen && *p-1U < 127) p++;
-+ if (*p>193 || (*p==193 && p[1]>254) || p>r+506)
-+ return -1;
-+ p += 5 + !!*p;
-+ }
-+ while (ancount--) {
-+ while (p-r < rlen && *p-1U < 127) p++;
-+ if (*p>193 || (*p==193 && p[1]>254) || p>r+506)
-+ return -1;
-+ p += 1 + !!*p;
-+ len = p[8]*256 + p[9];
-+ if (p+len > r+rlen) return -1;
-+ if (callback(ctx, p[1], p+10, len, r) < 0) return -1;
-+ p += 10 + len;
-+ }
-+ return 0;
-+}
-diff --git a/src/network/getaddrinfo.c b/src/network/getaddrinfo.c
-index 5d45be7..70b6cfd 100644
---- a/src/network/getaddrinfo.c
-+++ b/src/network/getaddrinfo.c
-@@ -1,249 +1,115 @@
- #include <stdlib.h>
--#include <stdio.h>
--#include <netdb.h>
--#include <netinet/in.h>
- #include <sys/socket.h>
--#include <unistd.h>
-+#include <netinet/in.h>
-+#include <netdb.h>
- #include <string.h>
--#include <ctype.h>
--#include "__dns.h"
--#include "stdio_impl.h"
--
--static int is_valid(const char *host)
--{
-- const unsigned char *s;
-- if (strlen(host)-1 > 254 || mbstowcs(0, host, 0) > 255) return 0;
-- for (s=(void *)host; *s>=0x80 || *s=='.' || *s=='-' || isalnum(*s); s++);
-- return !*s;
--}
--
--#if 0
--static int have_af(int family)
--{
-- struct sockaddr_in6 sin6 = { .sin6_family = family };
-- socklen_t sl = family == AF_INET
-- ? sizeof(struct sockaddr_in)
-- : sizeof(struct sockaddr_in6);
-- int sock = socket(family, SOCK_STREAM, 0);
-- int have = !bind(sock, (void *)&sin6, sl);
-- close(sock);
-- return have;
--}
--#endif
--
--union sa {
-- struct sockaddr_in sin;
-- struct sockaddr_in6 sin6;
--};
--
--struct aibuf {
-- struct addrinfo ai;
-- union sa sa;
--};
--
--/* Extra slots needed for storing canonical name */
--#define EXTRA ((256+sizeof(struct aibuf)-1)/sizeof(struct aibuf))
-+#include "lookup.h"
-
- int getaddrinfo(const char *restrict host, const char *restrict serv, const struct addrinfo *restrict hint, struct addrinfo **restrict res)
- {
-- int flags = hint ? hint->ai_flags : 0;
-- int family = hint ? hint->ai_family : AF_UNSPEC;
-- int type = hint ? hint->ai_socktype : 0;
-- int proto = hint ? hint->ai_protocol : 0;
-- unsigned long port = 0;
-- struct aibuf *buf;
-- union sa sa = {{0}};
-- unsigned char reply[1024];
-- int i, j;
-- char line[512];
-- FILE *f, _f;
-- unsigned char _buf[1024];
-- char *z;
-- int result;
-- int cnt;
--
-- if (family != AF_INET && family != AF_INET6 && family != AF_UNSPEC)
-- return EAI_FAMILY;
--
-- if (host && strlen(host)>255) return EAI_NONAME;
-- if (serv && strlen(serv)>32) return EAI_SERVICE;
--
-- if (type && !proto)
-- proto = type==SOCK_DGRAM ? IPPROTO_UDP : IPPROTO_TCP;
-- if (!type && proto)
-- type = proto==IPPROTO_UDP ? SOCK_DGRAM : SOCK_STREAM;
--
-- if (serv) {
-- if (!*serv) return EAI_SERVICE;
-- port = strtoul(serv, &z, 10);
-- if (*z) {
-- size_t servlen = strlen(serv);
-- char *end = line;
--
-- if (flags & AI_NUMERICSERV) return EAI_SERVICE;
-+ struct service ports[MAXSERVS];
-+ struct address addrs[MAXADDRS];
-+ char canon[256], *outcanon;
-+ int nservs, naddrs, nais, canon_len, i, j, k;
-+ int family = AF_UNSPEC, flags = 0, proto = 0;
-+ struct aibuf {
-+ struct addrinfo ai;
-+ union sa {
-+ struct sockaddr_in sin;
-+ struct sockaddr_in6 sin6;
-+ } sa;
-+ } *out;
-+
-+ if (hint) {
-+ family = hint->ai_family;
-+ flags = hint->ai_flags;
-+ proto = hint->ai_protocol;
-+
-+ const int mask = AI_PASSIVE | AI_CANONNAME | AI_NUMERICHOST |
-+ AI_V4MAPPED | AI_ALL | AI_ADDRCONFIG | AI_NUMERICSERV;
-+ if ((flags & mask) != flags)
-+ return EAI_BADFLAGS;
-+
-+ switch (family) {
-+ case AF_INET:
-+ case AF_INET6:
-+ case AF_UNSPEC:
-+ break;
-+ default:
-+ return EAI_FAMILY;
-+ }
-
-- f = __fopen_rb_ca("/etc/services", &_f, _buf, sizeof _buf);
-- if (!f) return EAI_SERVICE;
-- while (fgets(line, sizeof line, f)) {
-- if (strncmp(line, serv, servlen) || !isspace(line[servlen]))
-- continue;
-- port = strtoul(line+servlen, &end, 10);
-- if (strncmp(end, proto==IPPROTO_UDP ? "/udp" : "/tcp", 4))
-- continue;
-+ switch (hint->ai_socktype) {
-+ case SOCK_STREAM:
-+ switch (proto) {
-+ case 0:
-+ proto = IPPROTO_TCP;
-+ case IPPROTO_TCP:
- break;
-+ default:
-+ return EAI_SERVICE;
- }
-- __fclose_ca(f);
-- if (feof(f)) return EAI_SERVICE;
-- }
-- if (port > 65535) return EAI_SERVICE;
-- port = htons(port);
-- }
--
-- if (!host) {
-- if (family == AF_UNSPEC) {
-- cnt = 2; family = AF_INET;
-- } else {
-- cnt = 1;
-- }
-- buf = calloc(sizeof *buf, cnt);
-- if (!buf) return EAI_MEMORY;
-- for (i=0; i<cnt; i++) {
-- if (i) family = AF_INET6;
-- buf[i].ai.ai_protocol = proto;
-- buf[i].ai.ai_socktype = type;
-- buf[i].ai.ai_addr = (void *)&buf[i].sa;
-- buf[i].ai.ai_addrlen = family==AF_INET6
-- ? sizeof sa.sin6 : sizeof sa.sin;
-- buf[i].ai.ai_family = family;
-- buf[i].sa.sin.sin_family = family;
-- buf[i].sa.sin.sin_port = port;
-- if (i+1<cnt) buf[i].ai.ai_next = &buf[i+1].ai;
-- if (!(flags & AI_PASSIVE)) {
-- if (family == AF_INET) {
-- 0[(uint8_t*)&buf[i].sa.sin.sin_addr.s_addr]=127;
-- 3[(uint8_t*)&buf[i].sa.sin.sin_addr.s_addr]=1;
-- } else buf[i].sa.sin6.sin6_addr.s6_addr[15] = 1;
-+ break;
-+ case SOCK_DGRAM:
-+ switch (proto) {
-+ case 0:
-+ proto = IPPROTO_UDP;
-+ case IPPROTO_UDP:
-+ break;
-+ default:
-+ return EAI_SERVICE;
- }
-+ case 0:
-+ break;
-+ default:
-+ return EAI_SOCKTYPE;
- }
-- *res = &buf->ai;
-- return 0;
-- }
--
-- if (!*host) return EAI_NONAME;
--
-- /* Try as a numeric address */
-- if (__ipparse(&sa, family, host) >= 0) {
-- buf = calloc(sizeof *buf, 1+EXTRA);
-- if (!buf) return EAI_MEMORY;
-- family = sa.sin.sin_family;
-- buf->ai.ai_protocol = proto;
-- buf->ai.ai_socktype = type;
-- buf->ai.ai_addr = (void *)&buf->sa;
-- buf->ai.ai_addrlen = family==AF_INET6 ? sizeof sa.sin6 : sizeof sa.sin;
-- buf->ai.ai_family = family;
-- buf->ai.ai_canonname = (char *)host;
-- buf->sa = sa;
-- buf->sa.sin.sin_port = port;
-- *res = &buf->ai;
-- return 0;
- }
-
-- if (flags & AI_NUMERICHOST) return EAI_NONAME;
-+ nservs = __lookup_serv(ports, serv, proto, flags);
-+ if (nservs < 0) return nservs;
-
-- f = __fopen_rb_ca("/etc/hosts", &_f, _buf, sizeof _buf);
-- if (f) while (fgets(line, sizeof line, f)) {
-- char *p;
-- size_t l = strlen(host);
-+ naddrs = __lookup_name(addrs, canon, host, family, flags);
-+ if (naddrs < 0) return naddrs;
-
-- if ((p=strchr(line, '#'))) *p++='\n', *p=0;
-- for(p=line+1; (p=strstr(p, host)) &&
-- (!isspace(p[-1]) || !isspace(p[l])); p++);
-- if (!p) continue;
-- __fclose_ca(f);
--
-- /* Isolate IP address to parse */
-- for (p=line; *p && !isspace(*p); p++);
-- *p++ = 0;
-- if (__ipparse(&sa, family, line) < 0) return EAI_NONAME;
--
-- /* Allocate and fill result buffer */
-- buf = calloc(sizeof *buf, 1+EXTRA);
-- if (!buf) return EAI_MEMORY;
-- family = sa.sin.sin_family;
-- buf->ai.ai_protocol = proto;
-- buf->ai.ai_socktype = type;
-- buf->ai.ai_addr = (void *)&buf->sa;
-- buf->ai.ai_addrlen = family==AF_INET6 ? sizeof sa.sin6 : sizeof sa.sin;
-- buf->ai.ai_family = family;
-- buf->sa = sa;
-- buf->sa.sin.sin_port = port;
--
-- /* Extract first name as canonical name */
-- for (; *p && isspace(*p); p++);
-- buf->ai.ai_canonname = (void *)(buf+1);
-- snprintf(buf->ai.ai_canonname, 256, "%s", p);
-- for (p=buf->ai.ai_canonname; *p && !isspace(*p); p++);
-- *p = 0;
-- if (!is_valid(buf->ai.ai_canonname))
-- buf->ai.ai_canonname = 0;
--
-- *res = &buf->ai;
-- return 0;
-- }
-- if (f) __fclose_ca(f);
-+ nais = nservs * naddrs;
-+ canon_len = strlen(canon);
-+ out = calloc(1, nais * sizeof(*out) + canon_len + 1);
-+ if (!out) return EAI_MEMORY;
-
--#if 0
-- f = __fopen_rb_ca("/etc/resolv.conf", &_f, _buf, sizeof _buf);
-- if (f) while (fgets(line, sizeof line, f)) {
-- if (!isspace(line[10]) || (strncmp(line, "search", 6)
-- && strncmp(line, "domain", 6))) continue;
-+ if (canon_len) {
-+ outcanon = (void *)&out[nais];
-+ memcpy(outcanon, canon, canon_len+1);
-+ } else {
-+ outcanon = 0;
- }
-- if (f) __fclose_ca(f);
--#endif
-
-- /* Perform one or more DNS queries for host */
-- memset(reply, 0, sizeof reply);
-- result = __dns_query(reply, host, family, 0);
-- if (result < 0) return result;
--
-- cnt = __dns_count_addrs(reply, result);
-- if (cnt <= 0) return EAI_NONAME;
--
-- buf = calloc(sizeof *buf, cnt+EXTRA);
-- if (!buf) return EAI_MEMORY;
--
-- i = 0;
-- if (family != AF_INET6) {
-- j = __dns_get_rr(&buf[i].sa.sin.sin_addr, sizeof *buf, 4, cnt-i, reply, RR_A, 0);
-- while (j--) buf[i++].sa.sin.sin_family = AF_INET;
-- }
-- if (family != AF_INET) {
-- j = __dns_get_rr(&buf[i].sa.sin6.sin6_addr, sizeof *buf, 16, cnt-i, reply, RR_AAAA, 0);
-- while (j--) buf[i++].sa.sin.sin_family = AF_INET6;
-- }
-- if (result>1) {
-- j = __dns_get_rr(&buf[i].sa.sin.sin_addr, sizeof *buf, 4, cnt-i, reply+512, RR_A, 0);
-- while (j--) buf[i++].sa.sin.sin_family = AF_INET;
-- j = __dns_get_rr(&buf[i].sa.sin6.sin6_addr, sizeof *buf, 16, cnt-i, reply+512, RR_AAAA, 0);
-- while (j--) buf[i++].sa.sin.sin_family = AF_INET6;
-- }
--
-- if (__dns_get_rr((void *)&buf[cnt], 0, 256, 1, reply, RR_CNAME, 1) <= 0)
-- strcpy((void *)&buf[cnt], host);
--
-- for (i=0; i<cnt; i++) {
-- buf[i].ai.ai_protocol = proto;
-- buf[i].ai.ai_socktype = type;
-- buf[i].ai.ai_addr = (void *)&buf[i].sa;
-- buf[i].ai.ai_addrlen = buf[i].sa.sin.sin_family==AF_INET6
-- ? sizeof sa.sin6 : sizeof sa.sin;
-- buf[i].ai.ai_family = buf[i].sa.sin.sin_family;
-- buf[i].sa.sin.sin_port = port;
-- buf[i].ai.ai_next = &buf[i+1].ai;
-- buf[i].ai.ai_canonname = (void *)&buf[cnt];
-+ for (k=i=0; i<naddrs; i++) for (j=0; j<nservs; j++, k++) {
-+ out[k].ai = (struct addrinfo){
-+ .ai_family = addrs[i].family,
-+ .ai_socktype = ports[j].proto == IPPROTO_TCP
-+ ? SOCK_STREAM : SOCK_DGRAM,
-+ .ai_protocol = ports[j].proto,
-+ .ai_addrlen = addrs[i].family == AF_INET
-+ ? sizeof(struct sockaddr_in)
-+ : sizeof(struct sockaddr_in6),
-+ .ai_addr = (void *)&out[k].sa,
-+ .ai_canonname = outcanon,
-+ .ai_next = &out[k+1].ai };
-+ switch (addrs[i].family) {
-+ case AF_INET:
-+ out[k].sa.sin.sin_family = AF_INET;
-+ out[k].sa.sin.sin_port = htons(ports[j].port);
-+ memcpy(&out[k].sa.sin.sin_addr, &addrs[i].addr, 4);
-+ break;
-+ case AF_INET6:
-+ out[k].sa.sin6.sin6_family = AF_INET6;
-+ out[k].sa.sin6.sin6_port = htons(ports[j].port);
-+ memcpy(&out[k].sa.sin6.sin6_addr, &addrs[i].addr, 16);
-+ break;
-+ }
- }
-- buf[cnt-1].ai.ai_next = 0;
-- *res = &buf->ai;
--
-+ out[nais-1].ai.ai_next = 0;
-+ *res = &out->ai;
- return 0;
- }
-diff --git a/src/network/gethostbyname2_r.c b/src/network/gethostbyname2_r.c
-index 27eb080..aa8b0a9 100644
---- a/src/network/gethostbyname2_r.c
-+++ b/src/network/gethostbyname2_r.c
-@@ -6,41 +6,31 @@
- #include <netinet/in.h>
- #include <errno.h>
- #include <stdint.h>
-+#include "lookup.h"
-
- int gethostbyname2_r(const char *name, int af,
- struct hostent *h, char *buf, size_t buflen,
- struct hostent **res, int *err)
- {
-- struct addrinfo hint = {
-- .ai_family = af==AF_INET6 ? af : AF_INET,
-- .ai_flags = AI_CANONNAME
-- };
-- struct addrinfo *ai, *p;
-- int i;
-- size_t need;
-- const char *canon;
-+ struct address addrs[MAXADDRS];
-+ char canon[256];
-+ int i, cnt;
-+ size_t align, need;
-
-- af = hint.ai_family;
--
-- /* Align buffer */
-- i = (uintptr_t)buf & sizeof(char *)-1;
-- if (i) {
-- if (buflen < sizeof(char *)-i) return ERANGE;
-- buf += sizeof(char *)-i;
-- buflen -= sizeof(char *)-i;
-- }
--
-- switch (getaddrinfo(name, 0, &hint, &ai)) {
-+ cnt = __lookup_name(addrs, canon, name, af, AI_CANONNAME);
-+ if (cnt<0) switch (cnt) {
- case EAI_NONAME:
- *err = HOST_NOT_FOUND;
-- return errno;
-+ return ENOENT;
- case EAI_AGAIN:
- *err = TRY_AGAIN;
-- return errno;
-+ return EAGAIN;
- default:
-+ case EAI_FAIL:
-+ *err = NO_RECOVERY;
-+ return EBADMSG;
- case EAI_MEMORY:
- case EAI_SYSTEM:
-- case EAI_FAIL:
- *err = NO_RECOVERY;
- return errno;
- case 0:
-@@ -50,22 +40,22 @@ int gethostbyname2_r(const char *name, int af,
- h->h_addrtype = af;
- h->h_length = af==AF_INET6 ? 16 : 4;
-
-- canon = ai->ai_canonname ? ai->ai_canonname : name;
-+ /* Align buffer */
-+ align = -(uintptr_t)buf & sizeof(char *)-1;
-+
- need = 4*sizeof(char *);
-- for (i=0, p=ai; p; i++, p=p->ai_next)
-- need += sizeof(char *) + h->h_length;
-+ need += (cnt + 1) * (sizeof(char *) + h->h_length);
- need += strlen(name)+1;
- need += strlen(canon)+1;
-+ need += align;
-
-- if (need > buflen) {
-- freeaddrinfo(ai);
-- return ERANGE;
-- }
-+ if (need > buflen) return ERANGE;
-
-+ buf += align;
- h->h_aliases = (void *)buf;
- buf += 3*sizeof(char *);
- h->h_addr_list = (void *)buf;
-- buf += (i+1)*sizeof(char *);
-+ buf += (cnt+1)*sizeof(char *);
-
- h->h_name = h->h_aliases[0] = buf;
- strcpy(h->h_name, canon);
-@@ -79,16 +69,13 @@ int gethostbyname2_r(const char *name, int af,
-
- h->h_aliases[2] = 0;
-
-- for (i=0, p=ai; p; i++, p=p->ai_next) {
-+ for (i=0; i<cnt; i++) {
- h->h_addr_list[i] = (void *)buf;
- buf += h->h_length;
-- memcpy(h->h_addr_list[i],
-- &((struct sockaddr_in *)p->ai_addr)->sin_addr,
-- h->h_length);
-+ memcpy(h->h_addr_list[i], addrs[i].addr, h->h_length);
- }
- h->h_addr_list[i] = 0;
-
- *res = h;
-- freeaddrinfo(ai);
- return 0;
- }
-diff --git a/src/network/getnameinfo.c b/src/network/getnameinfo.c
-index 33f89a3..dfcf6ed 100644
---- a/src/network/getnameinfo.c
-+++ b/src/network/getnameinfo.c
-@@ -5,15 +5,50 @@
- #include <sys/socket.h>
- #include <netinet/in.h>
- #include <arpa/inet.h>
--#include "__dns.h"
-+
-+int __dns_parse(const unsigned char *, int, int (*)(void *, int, const void *, int, const void *), void *);
-+int __dn_expand(const unsigned char *, const unsigned char *, const unsigned char *, char *, int);
-+int __res_mkquery(int, const char *, int, int, const unsigned char *, int, const unsigned char*, unsigned char *, int);
-+int __res_send(const unsigned char *, int, unsigned char *, int);
-+
-+#define PTR_MAX (64 + sizeof ".in-addr.arpa")
-+#define RR_PTR 12
-+
-+static void mkptr4(char *s, const unsigned char *ip)
-+{
-+ sprintf(s, "%d.%d.%d.%d.in-addr.arpa",
-+ ip[3], ip[2], ip[1], ip[0]);
-+}
-+
-+static void mkptr6(char *s, const unsigned char *ip)
-+{
-+ static const char xdigits[] = "0123456789abcdef";
-+ int i;
-+ for (i=15; i>=0; i--) {
-+ *s++ = xdigits[ip[i]&15]; *s++ = '.';
-+ *s++ = xdigits[ip[i]>>4]; *s++ = '.';
-+ }
-+ strcpy(s, "ip6.arpa");
-+}
-+
-+static int dns_parse_callback(void *c, int rr, const void *data, int len, const void *packet)
-+{
-+ char tmp[256];
-+ if (rr != RR_PTR) return 0;
-+ if (__dn_expand(packet, (const unsigned char *)packet + 512,
-+ data, tmp, sizeof tmp) > 0)
-+ strcpy(c, tmp);
-+ return 0;
-+
-+}
-
- int getnameinfo(const struct sockaddr *restrict sa, socklen_t sl,
- char *restrict node, socklen_t nodelen,
- char *restrict serv, socklen_t servlen,
- int flags)
- {
-+ char ptr[PTR_MAX];
- char buf[256];
-- unsigned char reply[512];
- int af = sa->sa_family;
- unsigned char *a;
-
-@@ -21,20 +56,32 @@ int getnameinfo(const struct sockaddr *restrict sa, socklen_t sl,
- case AF_INET:
- a = (void *)&((struct sockaddr_in *)sa)->sin_addr;
- if (sl != sizeof(struct sockaddr_in)) return EAI_FAMILY;
-+ mkptr4(ptr, a);
- break;
- case AF_INET6:
- a = (void *)&((struct sockaddr_in6 *)sa)->sin6_addr;
- if (sl != sizeof(struct sockaddr_in6)) return EAI_FAMILY;
-+ if (memcmp(a, "\0\0\0\0\0\0\0\0\0\0\xff\xff", 12))
-+ mkptr6(ptr, a);
-+ else
-+ mkptr4(ptr, a+12);
- break;
- default:
- return EAI_FAMILY;
- }
-
- if (node && nodelen) {
-- if ((flags & NI_NUMERICHOST)
-- || __dns_query(reply, a, af, 1) <= 0
-- || __dns_get_rr(buf, 0, 256, 1, reply, RR_PTR, 1) <= 0)
-- {
-+ buf[0] = 0;
-+ if (!(flags & NI_NUMERICHOST)) {
-+ unsigned char query[18+PTR_MAX], reply[512];
-+ int qlen = __res_mkquery(0, ptr, 1, RR_PTR,
-+ 0, 0, 0, query, sizeof query);
-+ int rlen = __res_send(query, qlen, reply, sizeof reply);
-+ buf[0] = 0;
-+ if (rlen > 0)
-+ __dns_parse(reply, rlen, dns_parse_callback, buf);
-+ }
-+ if (!*buf) {
- if (flags & NI_NAMEREQD) return EAI_NONAME;
- inet_ntop(af, a, buf, sizeof buf);
- }
-diff --git a/src/network/getservbyname.c b/src/network/getservbyname.c
-index 0b00ce1..dd30376 100644
---- a/src/network/getservbyname.c
-+++ b/src/network/getservbyname.c
-@@ -4,7 +4,7 @@
- struct servent *getservbyname(const char *name, const char *prots)
- {
- static struct servent se;
-- static long buf[32/sizeof(long)];
-+ static char *buf[2];
- struct servent *res;
- if (getservbyname_r(name, prots, &se, (void *)buf, sizeof buf, &res))
- return 0;
-diff --git a/src/network/getservbyname_r.c b/src/network/getservbyname_r.c
-index 811c174..8cdf622 100644
---- a/src/network/getservbyname_r.c
-+++ b/src/network/getservbyname_r.c
-@@ -5,49 +5,43 @@
- #include <inttypes.h>
- #include <errno.h>
- #include <string.h>
-+#include "lookup.h"
-+
-+#define ALIGN (sizeof(struct { char a; char *b; }) - sizeof(char *))
-
- int getservbyname_r(const char *name, const char *prots,
- struct servent *se, char *buf, size_t buflen, struct servent **res)
- {
-- struct addrinfo *ai, hint = { .ai_family = AF_INET };
-- int i;
--
-- if (!prots) {
-- int r = getservbyname_r(name, "tcp", se, buf, buflen, res);
-- if (r) r = getservbyname_r(name, "udp", se, buf, buflen, res);
-- return r;
-- }
-+ struct service servs[MAXSERVS];
-+ int cnt, proto, align;
-
- /* Align buffer */
-- i = (uintptr_t)buf & sizeof(char *)-1;
-- if (!i) i = sizeof(char *);
-- if (buflen < 3*sizeof(char *)-i)
-+ align = -(uintptr_t)buf & ALIGN-1;
-+ if (buflen < 2*sizeof(char *)+align)
- return ERANGE;
-- buf += sizeof(char *)-i;
-- buflen -= sizeof(char *)-i;
-+ buf += align;
-
-- if (!strcmp(prots, "tcp")) hint.ai_protocol = IPPROTO_TCP;
-- else if (!strcmp(prots, "udp")) hint.ai_protocol = IPPROTO_UDP;
-+ if (!prots) proto = 0;
-+ else if (!strcmp(prots, "tcp")) proto = IPPROTO_TCP;
-+ else if (!strcmp(prots, "udp")) proto = IPPROTO_UDP;
- else return EINVAL;
-
-- switch (getaddrinfo(0, name, &hint, &ai)) {
-+ cnt = __lookup_serv(servs, name, proto, 0);
-+ if (cnt<0) switch (cnt) {
- case EAI_MEMORY:
- case EAI_SYSTEM:
- return ENOMEM;
- default:
- return ENOENT;
-- case 0:
-- break;
- }
-
- se->s_name = (char *)name;
- se->s_aliases = (void *)buf;
- se->s_aliases[0] = se->s_name;
- se->s_aliases[1] = 0;
-- se->s_port = ((struct sockaddr_in *)ai->ai_addr)->sin_port;
-- se->s_proto = (char *)prots;
-+ se->s_port = htons(servs[0].port);
-+ se->s_proto = servs[0].proto == IPPROTO_TCP ? "tcp" : "udp";
-
-- freeaddrinfo(ai);
- *res = se;
- return 0;
- }
-diff --git a/src/network/inet_addr.c b/src/network/inet_addr.c
-index ea0a8f7..10b21f2 100644
---- a/src/network/inet_addr.c
-+++ b/src/network/inet_addr.c
-@@ -1,11 +1,12 @@
- #include <sys/socket.h>
- #include <netinet/in.h>
- #include <arpa/inet.h>
--#include "__dns.h"
-+
-+int __inet_aton(const char *, struct in_addr *);
-
- in_addr_t inet_addr(const char *p)
- {
-- struct sockaddr_in sin;
-- if (__ipparse(&sin, AF_INET, p) < 0) return -1;
-- return sin.sin_addr.s_addr;
-+ struct in_addr a;
-+ if (!__inet_aton(p, &a)) return -1;
-+ return a.s_addr;
- }
-diff --git a/src/network/inet_aton.c b/src/network/inet_aton.c
-new file mode 100644
-index 0000000..0f9a45f
---- /dev/null
-+++ b/src/network/inet_aton.c
-@@ -0,0 +1,41 @@
-+#include <ctype.h>
-+#include <sys/socket.h>
-+#include <netinet/in.h>
-+#include <arpa/inet.h>
-+#include "libc.h"
-+
-+int __inet_aton(const char *s0, struct in_addr *dest)
-+{
-+ const char *s = s0;
-+ unsigned char *d = (void *)dest;
-+ unsigned long a[4] = { 0 };
-+ char *z;
-+ int i;
-+
-+ for (i=0; i<4; i++) {
-+ a[i] = strtoul(s, &z, 0);
-+ if (z==s || (*z && *z != '.') || !isdigit(*s))
-+ return 0;
-+ if (!*z) break;
-+ s=z+1;
-+ }
-+ if (i==4) return 0;
-+ switch (i) {
-+ case 0:
-+ a[1] = a[0] & 0xffffff;
-+ a[0] >>= 24;
-+ case 1:
-+ a[2] = a[1] & 0xffff;
-+ a[1] >>= 16;
-+ case 2:
-+ a[3] = a[2] & 0xff;
-+ a[2] >>= 8;
-+ }
-+ for (i=0; i<4; i++) {
-+ if (a[i] > 255) return 0;
-+ d[i] = a[i];
-+ }
-+ return 1;
-+}
-+
-+weak_alias(__inet_aton, inet_aton);
-diff --git a/src/network/inet_legacy.c b/src/network/inet_legacy.c
-index de5b75c..621b47b 100644
---- a/src/network/inet_legacy.c
-+++ b/src/network/inet_legacy.c
-@@ -1,21 +1,12 @@
- #include <sys/socket.h>
- #include <netinet/in.h>
- #include <arpa/inet.h>
--#include "__dns.h"
-
- in_addr_t inet_network(const char *p)
- {
- return ntohl(inet_addr(p));
- }
-
--int inet_aton(const char *cp, struct in_addr *inp)
--{
-- struct sockaddr_in sin;
-- if (__ipparse(&sin, AF_INET, cp) < 0) return 0;
-- *inp = sin.sin_addr;
-- return 1;
--}
--
- struct in_addr inet_makeaddr(in_addr_t n, in_addr_t h)
- {
- if (n < 256) h |= n<<24;
-diff --git a/src/network/lookup.h b/src/network/lookup.h
-new file mode 100644
-index 0000000..82c969e
---- /dev/null
-+++ b/src/network/lookup.h
-@@ -0,0 +1,26 @@
-+#ifndef LOOKUP_H
-+#define LOOKUP_H
-+
-+#include <stdint.h>
-+
-+struct address {
-+ int family;
-+ unsigned scopeid;
-+ uint8_t addr[16];
-+};
-+
-+struct service {
-+ uint16_t port;
-+ char proto;
-+};
-+
-+/* The limit of 48 results is a non-sharp bound on the number of addresses
-+ * that can fit in one 512-byte DNS packet full of v4 results and a second
-+ * packet full of v6 results. Due to headers, the actual limit is lower. */
-+#define MAXADDRS 48
-+#define MAXSERVS 2
-+
-+int __lookup_serv(struct service buf[static MAXSERVS], const char *name, int proto, int flags);
-+int __lookup_name(struct address buf[static MAXADDRS], char canon[static 256], const char *name, int family, int flags);
-+
-+#endif
-diff --git a/src/network/lookup_name.c b/src/network/lookup_name.c
-new file mode 100644
-index 0000000..8d41627
---- /dev/null
-+++ b/src/network/lookup_name.c
-@@ -0,0 +1,210 @@
-+#include <sys/socket.h>
-+#include <netinet/in.h>
-+#include <netdb.h>
-+#include <arpa/inet.h>
-+#include <ctype.h>
-+#include <stdlib.h>
-+#include <string.h>
-+#include <fcntl.h>
-+#include "lookup.h"
-+#include "stdio_impl.h"
-+#include "syscall.h"
-+
-+static int is_valid_hostname(const char *host)
-+{
-+ const unsigned char *s;
-+ if (strnlen(host, 256)-1 > 254 || mbstowcs(0, host, 0) > 255) return 0;
-+ for (s=(void *)host; *s>=0x80 || *s=='.' || *s=='-' || isalnum(*s); s++);
-+ return !*s;
-+}
-+
-+static int name_from_null(struct address buf[static 2], const char *name, int family, int flags)
-+{
-+ int cnt = 0;
-+ if (name) return 0;
-+ if (flags & AI_PASSIVE) {
-+ if (family != AF_INET6)
-+ buf[cnt++] = (struct address){ .family = AF_INET };
-+ if (family != AF_INET)
-+ buf[cnt++] = (struct address){ .family = AF_INET6 };
-+ } else {
-+ if (family != AF_INET6)
-+ buf[cnt++] = (struct address){ .family = AF_INET, .addr = { 127,0,0,1 } };
-+ if (family != AF_INET)
-+ buf[cnt++] = (struct address){ .family = AF_INET6, .addr = { [15] = 1 } };
-+ }
-+ return cnt;
-+}
-+
-+int __inet_aton(const char *, struct in_addr *);
-+
-+static int name_from_numeric(struct address buf[static 1], const char *name, int family)
-+{
-+ struct in_addr a4;
-+ struct in6_addr a6;
-+ if (family != AF_INET6 && __inet_aton(name, &a4)>0) {
-+ memcpy(&buf[0].addr, &a4, sizeof a4);
-+ buf[0].family = AF_INET;
-+ return 1;
-+ }
-+ if (family != AF_INET && inet_pton(AF_INET6, name, &a6)>0) {
-+ memcpy(&buf[0].addr, &a6, sizeof a6);
-+ buf[0].family = AF_INET6;
-+ return 1;
-+ }
-+ return 0;
-+}
-+
-+static int name_from_hosts(struct address buf[static MAXADDRS], char canon[static 256], const char *name, int family)
-+{
-+ char line[512];
-+ size_t l = strlen(name);
-+ int cnt = 0;
-+ unsigned char _buf[1032];
-+ FILE _f, *f = __fopen_rb_ca("/etc/hosts", &_f, _buf, sizeof _buf);
-+ if (!f) return 0;
-+ while (fgets(line, sizeof line, f) && cnt < MAXADDRS) {
-+ char *p, *z;
-+
-+ if ((p=strchr(line, '#'))) *p++='\n', *p=0;
-+ for(p=line+1; (p=strstr(p, name)) &&
-+ (!isspace(p[-1]) || !isspace(p[l])); p++);
-+ if (!p) continue;
-+
-+ /* Isolate IP address to parse */
-+ for (p=line; *p && !isspace(*p); p++);
-+ *p++ = 0;
-+ if (name_from_numeric(buf+cnt, line, family))
-+ cnt++;
-+
-+ /* Extract first name as canonical name */
-+ for (; *p && isspace(*p); p++);
-+ for (z=p; *z && !isspace(*z); z++);
-+ *z = 0;
-+ if (is_valid_hostname(p)) memcpy(canon, p, z-p+1);
-+ }
-+ __fclose_ca(f);
-+ return cnt;
-+}
-+
-+struct dpc_ctx {
-+ struct address *addrs;
-+ char *canon;
-+ int cnt;
-+};
-+
-+int __dns_parse(const unsigned char *, int, int (*)(void *, int, const void *, int, const void *), void *);
-+int __dn_expand(const unsigned char *, const unsigned char *, const unsigned char *, char *, int);
-+int __res_mkquery(int, const char *, int, int, const unsigned char *, int, const unsigned char*, unsigned char *, int);
-+int __res_msend(int, const unsigned char *const *, const int *, unsigned char *const *, int *, int);
-+
-+#define RR_A 1
-+#define RR_CNAME 5
-+#define RR_AAAA 28
-+
-+static int dns_parse_callback(void *c, int rr, const void *data, int len, const void *packet)
-+{
-+ char tmp[256];
-+ struct dpc_ctx *ctx = c;
-+ switch (rr) {
-+ case RR_A:
-+ if (len != 4) return -1;
-+ ctx->addrs[ctx->cnt].family = AF_INET;
-+ memcpy(ctx->addrs[ctx->cnt++].addr, data, 4);
-+ break;
-+ case RR_AAAA:
-+ if (len != 16) return -1;
-+ ctx->addrs[ctx->cnt].family = AF_INET6;
-+ memcpy(ctx->addrs[ctx->cnt++].addr, data, 16);
-+ break;
-+ case RR_CNAME:
-+ if (__dn_expand(packet, (const unsigned char *)packet + 512,
-+ data, tmp, sizeof tmp) > 0 && is_valid_hostname(tmp))
-+ strcpy(ctx->canon, tmp);
-+ break;
-+ }
-+ return 0;
-+}
-+
-+static int name_from_dns(struct address buf[static MAXADDRS], char canon[static 256], const char *name, int family)
-+{
-+ unsigned char qbuf[2][280], abuf[2][512];
-+ const unsigned char *qp[2] = { qbuf[0], qbuf[1] };
-+ unsigned char *ap[2] = { abuf[0], abuf[1] };
-+ int qlens[2], alens[2];
-+ int i, nq = 0;
-+ struct dpc_ctx ctx = { .addrs = buf, .canon = canon };
-+
-+ if (family != AF_INET6) {
-+ qlens[nq] = __res_mkquery(0, name, 1, RR_A, 0, 0, 0,
-+ qbuf[nq], sizeof *qbuf);
-+ nq++;
-+ }
-+ if (family != AF_INET) {
-+ qlens[nq] = __res_mkquery(0, name, 1, RR_AAAA, 0, 0, 0,
-+ qbuf[nq], sizeof *qbuf);
-+ nq++;
-+ }
-+
-+ if (__res_msend(nq, qp, qlens, ap, alens, sizeof *abuf) < 0) return EAI_SYSTEM;
-+
-+ for (i=0; i<nq; i++)
-+ __dns_parse(abuf[i], alens[i], dns_parse_callback, &ctx);
-+
-+ return ctx.cnt;
-+}
-+
-+int __lookup_name(struct address buf[static MAXADDRS], char canon[static 256], const char *name, int family, int flags)
-+{
-+ int cnt = 0, i, j;
-+
-+ *canon = 0;
-+ if (name) {
-+ size_t l;
-+ if ((l = strnlen(name, 256))-1 > 254)
-+ return EAI_NONAME;
-+ memcpy(canon, name, l+1);
-+ }
-+
-+ /* Procedurally, a request for v6 addresses with the v4-mapped
-+ * flag set is like a request for unspecified family, followed
-+ * by filtering of the results. */
-+ if (flags & AI_V4MAPPED) {
-+ if (family == AF_INET6) family = AF_UNSPEC;
-+ else flags -= AI_V4MAPPED;
-+ }
-+
-+ /* Try each backend until there's at least one result. */
-+ cnt = name_from_null(buf, name, family, flags);
-+ if (cnt<=0) cnt = name_from_numeric(buf, name, family);
-+ if (cnt<=0 && !(flags & AI_NUMERICHOST)) {
-+ cnt = name_from_hosts(buf, canon, name, family);
-+ if (cnt<=0) cnt = name_from_dns(buf, canon, name, family);
-+ }
-+ if (cnt<=0) return cnt ? cnt : EAI_NONAME;
-+
-+ /* Filter/transform results for v4-mapped lookup, if requested. */
-+ if (flags & AI_V4MAPPED) {
-+ if (!(flags & AI_ALL)) {
-+ /* If any v6 results exist, remove v4 results. */
-+ for (i=0; i<cnt && buf[i].family != AF_INET6; i++);
-+ if (i<cnt) {
-+ for (j=0; i<cnt; i++) {
-+ if (buf[i].family == AF_INET6)
-+ buf[j++] = buf[i];
-+ }
-+ cnt = i = j;
-+ }
-+ }
-+ /* Translate any remaining v4 results to v6 */
-+ for (i=0; i<cnt; i++) {
-+ if (buf[i].family != AF_INET) continue;
-+ memcpy(buf[i].addr+12, buf[i].addr, 4);
-+ memcpy(buf[i].addr, "\0\0\0\0\0\0\0\0\0\0\xff\xff", 12);
-+ buf[i].scopeid = 0;
-+ buf[i].family = AF_INET6;
-+ }
-+ }
-+
-+ return cnt;
-+}
-diff --git a/src/network/lookup_serv.c b/src/network/lookup_serv.c
-new file mode 100644
-index 0000000..bf4cba0
---- /dev/null
-+++ b/src/network/lookup_serv.c
-@@ -0,0 +1,72 @@
-+#include <sys/socket.h>
-+#include <netinet/in.h>
-+#include <netdb.h>
-+#include <ctype.h>
-+#include <string.h>
-+#include <fcntl.h>
-+#include "lookup.h"
-+#include "stdio_impl.h"
-+
-+int __lookup_serv(struct service buf[static MAXSERVS], const char *name, int proto, int flags)
-+{
-+ char line[128];
-+ int cnt = 0;
-+ char *p, *z = "";
-+ unsigned long port = 0;
-+
-+ if (name) {
-+ if (!*name) return EAI_SERVICE;
-+ port = strtoul(name, &z, 10);
-+ }
-+ if (!*z) {
-+ if (port > 65535) return EAI_SERVICE;
-+ if (proto != IPPROTO_UDP) {
-+ buf[cnt].port = port;
-+ buf[cnt++].proto = IPPROTO_TCP;
-+ }
-+ if (proto != IPPROTO_TCP) {
-+ buf[cnt].port = port;
-+ buf[cnt++].proto = IPPROTO_UDP;
-+ }
-+ return cnt;
-+ }
-+
-+ if (flags & AI_NUMERICSERV) return EAI_SERVICE;
-+
-+ size_t l = strlen(name);
-+
-+ unsigned char _buf[1032];
-+ FILE _f, *f = __fopen_rb_ca("/etc/services", &_f, _buf, sizeof _buf);
-+ if (!f) return EAI_SERVICE;
-+
-+ while (fgets(line, sizeof line, f) && cnt < MAXSERVS) {
-+ if ((p=strchr(line, '#'))) *p++='\n', *p=0;
-+
-+ /* Find service name */
-+ for(p=line; (p=strstr(p, name)); p++) {
-+ if (p>line && !isspace(p[-1])) continue;
-+ if (p[l] && !isspace(p[l])) continue;
-+ break;
-+ }
-+ if (!p) continue;
-+
-+ /* Skip past canonical name at beginning of line */
-+ for (p=line; *p && !isspace(*p); p++);
-+ if (!p) continue;
-+
-+ port = strtoul(p, &z, 10);
-+ if (port > 65535 || z==p) continue;
-+ if (!strncmp(z, "/udp", 4)) {
-+ if (proto == IPPROTO_TCP) continue;
-+ buf[cnt].port = port;
-+ buf[cnt++].proto = IPPROTO_UDP;
-+ }
-+ if (!strncmp(z, "/tcp", 4)) {
-+ if (proto == IPPROTO_UDP) continue;
-+ buf[cnt].port = port;
-+ buf[cnt++].proto = IPPROTO_TCP;
-+ }
-+ }
-+ __fclose_ca(f);
-+ return cnt > 0 ? cnt : EAI_SERVICE;
-+}
-diff --git a/src/network/proto.c b/src/network/proto.c
-index 3d0f584..1b51e15 100644
---- a/src/network/proto.c
-+++ b/src/network/proto.c
-@@ -14,7 +14,11 @@ static const unsigned char protos[][8] = {
- "\021udp",
- "\026idp",
- "\051ipv6",
-+ "\057gre",
-+ "\062esp",
-+ "\063ah",
- "\072icmpv6",
-+ "\136ipip",
- "\377raw",
- "\0\0"
- };
-diff --git a/src/network/res_init.c b/src/network/res_init.c
-index cbd5b15..5dba9df 100644
---- a/src/network/res_init.c
-+++ b/src/network/res_init.c
-@@ -1,3 +1,5 @@
-+#include <resolv.h>
-+
- int res_init()
- {
- return 0;
-diff --git a/src/network/res_mkquery.c b/src/network/res_mkquery.c
-new file mode 100644
-index 0000000..f7e4e9c
---- /dev/null
-+++ b/src/network/res_mkquery.c
-@@ -0,0 +1,41 @@
-+#include <resolv.h>
-+#include <string.h>
-+#include <time.h>
-+#include "libc.h"
-+
-+int __res_mkquery(int op, const char *dname, int class, int type,
-+ const unsigned char *data, int datalen,
-+ const unsigned char *newrr, unsigned char *buf, int buflen)
-+{
-+ int id, i, j;
-+ unsigned char q[280];
-+ struct timespec ts;
-+ size_t l = strnlen(dname, 256);
-+
-+ if (l-1>=254 || buflen<18+l || op>15u || class>255u || type>255u)
-+ return -1;
-+
-+ /* Construct query template - ID will be filled later */
-+ memset(q, 0, 18+l);
-+ q[2] = op*8 + 1;
-+ q[5] = 1;
-+ memcpy((char *)q+13, dname, l);
-+ for (i=13; q[i]; i=j+1) {
-+ for (j=i; q[j] && q[j] != '.'; j++);
-+ if (j-i-1u > 62u) return -1;
-+ q[i-1] = j-i;
-+ }
-+ q[i+1] = type;
-+ q[i+3] = class;
-+
-+ /* Make a reasonably unpredictable id */
-+ clock_gettime(CLOCK_REALTIME, &ts);
-+ id = ts.tv_nsec + ts.tv_nsec/65536UL & 0xffff;
-+ q[0] = id/256;
-+ q[1] = id;
-+
-+ memcpy(buf, q, 18+l);
-+ return 18+l;
-+}
-+
-+weak_alias(__res_mkquery, res_mkquery);
-diff --git a/src/network/res_msend.c b/src/network/res_msend.c
-new file mode 100644
-index 0000000..a5b7793
---- /dev/null
-+++ b/src/network/res_msend.c
-@@ -0,0 +1,185 @@
-+#include <sys/socket.h>
-+#include <netinet/in.h>
-+#include <netdb.h>
-+#include <arpa/inet.h>
-+#include <stdint.h>
-+#include <string.h>
-+#include <poll.h>
-+#include <time.h>
-+#include <ctype.h>
-+#include <unistd.h>
-+#include <errno.h>
-+#include <pthread.h>
-+#include "stdio_impl.h"
-+#include "syscall.h"
-+
-+static void cleanup(void *p)
-+{
-+ __syscall(SYS_close, (intptr_t)p);
-+}
-+
-+static unsigned long mtime()
-+{
-+ struct timespec ts;
-+ clock_gettime(CLOCK_REALTIME, &ts);
-+ return (unsigned long)ts.tv_sec * 1000
-+ + ts.tv_nsec / 1000000;
-+}
-+
-+int __res_msend(int nqueries, const unsigned char *const *queries,
-+ const int *qlens, unsigned char *const *answers, int *alens, int asize)
-+{
-+ int fd;
-+ FILE *f, _f;
-+ unsigned char _buf[256];
-+ char line[64], *s, *z;
-+ int timeout = 5000, attempts = 2, retry_interval;
-+ union {
-+ struct sockaddr_in sin;
-+ struct sockaddr_in6 sin6;
-+ } sa = {0}, ns[3] = {{0}};
-+ socklen_t sl = sizeof sa.sin;
-+ int nns = 0;
-+ int family = AF_INET;
-+ int rlen;
-+ int next;
-+ int i, j;
-+ int cs;
-+ struct pollfd pfd;
-+ unsigned long t0, t1, t2;
-+
-+ pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs);
-+
-+ /* Get nameservers from resolv.conf, fallback to localhost */
-+ f = __fopen_rb_ca("/etc/resolv.conf", &_f, _buf, sizeof _buf);
-+ if (f) for (nns=0; nns<3 && fgets(line, sizeof line, f); ) {
-+ if (!strncmp(line, "options", 7) && isspace(line[7])) {
-+ unsigned long x;
-+ char *p, *z;
-+ p = strstr(line, "timeout:");
-+ if (p && isdigit(p[8])) {
-+ p += 8;
-+ x = strtoul(p, &z, 10);
-+ if (z != p) timeout = x < 30 ? x*1000 : 30000;
-+ }
-+ p = strstr(line, "attempts:");
-+ if (p && isdigit(p[9])) {
-+ p += 9;
-+ x = strtoul(p, &z, 10);
-+ if (z != p) attempts = x < 10 ? x : 10;
-+ if (!attempts) attempts = 1;
-+ }
-+ }
-+ if (strncmp(line, "nameserver", 10) || !isspace(line[10]))
-+ continue;
-+ for (s=line+11; isspace(*s); s++);
-+ for (z=s; *z && !isspace(*z); z++);
-+ *z=0;
-+
-+ if (inet_pton(AF_INET, s, &ns[nns].sin.sin_addr)>0) {
-+ ns[nns].sin.sin_port = htons(53);
-+ ns[nns++].sin.sin_family = AF_INET;
-+ } else if (inet_pton(AF_INET6, s, &ns[nns].sin6.sin6_addr)>0) {
-+ sl = sizeof sa.sin6;
-+ ns[nns].sin6.sin6_port = htons(53);
-+ ns[nns++].sin6.sin6_family = family = AF_INET6;
-+ }
-+ }
-+ if (f) __fclose_ca(f);
-+ if (!nns) {
-+ ns[0].sin.sin_family = AF_INET;
-+ ns[0].sin.sin_port = htons(53);
-+ ns[0].sin.sin_addr.s_addr = htonl(0x7f000001);
-+ nns=1;
-+ }
-+
-+ /* Get local address and open/bind a socket */
-+ sa.sin.sin_family = family;
-+ fd = socket(family, SOCK_DGRAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0);
-+
-+ /* Handle case where system lacks IPv6 support */
-+ if (fd < 0 && family == AF_INET6 && errno == EAFNOSUPPORT) {
-+ fd = socket(AF_INET, SOCK_DGRAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0);
-+ family = AF_INET;
-+ }
-+ if (fd < 0 || bind(fd, (void *)&sa, sl) < 0) return -1;
-+
-+ /* Past this point, there are no errors. Each individual query will
-+ * yield either no reply (indicated by zero length) or an answer
-+ * packet which is up to the caller to interpret. */
-+
-+ pthread_cleanup_push(cleanup, (void *)(intptr_t)fd);
-+ pthread_setcancelstate(cs, 0);
-+
-+ /* Convert any IPv4 addresses in a mixed environment to v4-mapped */
-+ if (family == AF_INET6) {
-+ setsockopt(fd, IPPROTO_IPV6, IPV6_V6ONLY, &(int){0}, sizeof 0);
-+ for (i=0; i<nns; i++) {
-+ if (ns[i].sin.sin_family != AF_INET) continue;
-+ memcpy(ns[i].sin6.sin6_addr.s6_addr+12,
-+ &ns[i].sin.sin_addr, 4);
-+ memcpy(ns[i].sin6.sin6_addr.s6_addr,
-+ "\0\0\0\0\0\0\0\0\0\0\xff\xff", 12);
-+ ns[i].sin6.sin6_family = AF_INET6;
-+ ns[i].sin6.sin6_flowinfo = 0;
-+ ns[i].sin6.sin6_scope_id = 0;
-+ }
-+ }
-+
-+ memset(alens, 0, sizeof *alens * nqueries);
-+
-+ pfd.fd = fd;
-+ pfd.events = POLLIN;
-+ retry_interval = timeout / attempts;
-+ next = 0;
-+ t0 = t2 = mtime();
-+ t1 = t2 - retry_interval;
-+
-+ for (; t2-t0 < timeout; t2=mtime()) {
-+ if (t2-t1 >= retry_interval) {
-+ /* Query all configured namservers in parallel */
-+ for (i=0; i<nqueries; i++)
-+ if (!alens[i])
-+ for (j=0; j<nns; j++)
-+ sendto(fd, queries[i],
-+ qlens[i], MSG_NOSIGNAL,
-+ (void *)&ns[j], sl);
-+ t1 = t2;
-+ }
-+
-+ /* Wait for a response, or until time to retry */
-+ if (poll(&pfd, 1, t1+retry_interval-t2) <= 0) continue;
-+
-+ while ((rlen = recvfrom(fd, answers[next], asize, 0,
-+ (void *)&sa, (socklen_t[1]){sl})) >= 0) {
-+
-+ /* Ignore non-identifiable packets (no query id) */
-+ if (rlen < 2) continue;
-+
-+ /* Ignore replies from addresses we didn't send to */
-+ for (i=0; i<nns && memcmp(ns+i, &sa, sl); i++);
-+ if (i==nns) continue;
-+
-+ /* Find which query this answer goes with, if any */
-+ for (i=next; i<nqueries && (
-+ answers[next][0] != queries[i][0] ||
-+ answers[next][1] != queries[i][1] ); i++);
-+ if (i==nqueries) continue;
-+ if (alens[i]) continue;
-+
-+ /* Store answer in the right slot, or update next
-+ * available temp slot if it's already in place. */
-+ alens[i] = rlen;
-+ if (i == next)
-+ for (; next<nqueries && alens[next]; next++);
-+ else
-+ memcpy(answers[i], answers[next], rlen);
-+
-+ if (next == nqueries) goto out;
-+ }
-+ }
-+out:
-+ pthread_cleanup_pop(1);
-+
-+ return 0;
-+}
-diff --git a/src/network/res_query.c b/src/network/res_query.c
-index 3847da3..2b4e4bb 100644
---- a/src/network/res_query.c
-+++ b/src/network/res_query.c
-@@ -1,25 +1,17 @@
--#define _GNU_SOURCE
- #include <resolv.h>
- #include <netdb.h>
--#include "__dns.h"
- #include "libc.h"
-
--int res_query(const char *name, int class, int type, unsigned char *dest, int len)
-+int __res_mkquery(int, const char *, int, int, const unsigned char *, int, const unsigned char*, unsigned char *, int);
-+int __res_send(const unsigned char *, int, unsigned char *, int);
-+
-+int __res_query(const char *name, int class, int type, unsigned char *dest, int len)
- {
-- if (class != 1 || len < 512)
-- return -1;
-- switch(__dns_doqueries(dest, name, &type, 1)) {
-- case EAI_NONAME:
-- h_errno = HOST_NOT_FOUND;
-- return -1;
-- case EAI_AGAIN:
-- h_errno = TRY_AGAIN;
-- return -1;
-- case EAI_FAIL:
-- h_errno = NO_RECOVERY;
-- return -1;
-- }
-- return 512;
-+ unsigned char q[280];
-+ int ql = __res_mkquery(0, name, class, type, 0, 0, 0, q, sizeof q);
-+ if (ql < 0) return ql;
-+ return __res_send(q, ql, dest, len);
- }
-
--weak_alias(res_query, res_search);
-+weak_alias(__res_query, res_query);
-+weak_alias(__res_query, res_search);
-diff --git a/src/network/res_querydomain.c b/src/network/res_querydomain.c
-new file mode 100644
-index 0000000..c746dbe
---- /dev/null
-+++ b/src/network/res_querydomain.c
-@@ -0,0 +1,14 @@
-+#include <resolv.h>
-+#include <string.h>
-+
-+int res_querydomain(const char *name, const char *domain, int class, int type, unsigned char *dest, int len)
-+{
-+ char tmp[256];
-+ size_t nl = strnlen(name, 256);
-+ size_t dl = strnlen(domain, 256);
-+ if (nl+dl+1 > 255) return -1;
-+ memcpy(tmp, name, nl);
-+ tmp[nl] = '.';
-+ memcpy(tmp+nl+1, domain, dl+1);
-+ return res_query(tmp, class, type, dest, len);
-+}
-diff --git a/src/network/res_send.c b/src/network/res_send.c
-new file mode 100644
-index 0000000..19cfe0f
---- /dev/null
-+++ b/src/network/res_send.c
-@@ -0,0 +1,12 @@
-+#include <resolv.h>
-+#include "libc.h"
-+
-+int __res_msend(int, const unsigned char *const *, const int *, unsigned char *const *, int *, int);
-+
-+int __res_send(const unsigned char *msg, int msglen, unsigned char *answer, int anslen)
-+{
-+ int r = __res_msend(1, &msg, &msglen, &answer, &anslen, anslen);
-+ return r<0 ? r : anslen;
-+}
-+
-+weak_alias(__res_send, res_send);
-diff --git a/src/process/fork.c b/src/process/fork.c
-index 864c7d7..f8cf21e 100644
---- a/src/process/fork.c
-+++ b/src/process/fork.c
-@@ -1,5 +1,6 @@
- #include <unistd.h>
- #include <string.h>
-+#include <signal.h>
- #include "syscall.h"
- #include "libc.h"
- #include "pthread_impl.h"
-@@ -16,7 +17,11 @@ pid_t fork(void)
- sigset_t set;
- __fork_handler(-1);
- __block_all_sigs(&set);
-+#ifdef SYS_fork
- ret = syscall(SYS_fork);
-+#else
-+ ret = syscall(SYS_clone, SIGCHLD, 0);
-+#endif
- if (libc.has_thread_pointer && !ret) {
- pthread_t self = __pthread_self();
- self->tid = self->pid = __syscall(SYS_getpid);
-diff --git a/src/process/posix_spawn.c b/src/process/posix_spawn.c
-index f675a13..08928b0 100644
---- a/src/process/posix_spawn.c
-+++ b/src/process/posix_spawn.c
-@@ -22,6 +22,20 @@ struct args {
-
- void __get_handler_set(sigset_t *);
-
-+static int __sys_dup2(int old, int new)
-+{
-+#ifdef SYS_dup2
-+ return __syscall(SYS_dup2, old, new);
-+#else
-+ if (old==new) {
-+ int r = __syscall(SYS_fcntl, old, F_GETFD);
-+ return r<0 ? r : old;
-+ } else {
-+ return __syscall(SYS_dup3, old, new, 0);
-+ }
-+#endif
-+}
-+
- static int child(void *args_vp)
- {
- int i, ret;
-@@ -92,15 +106,14 @@ static int child(void *args_vp)
- goto fail;
- break;
- case FDOP_DUP2:
-- if ((ret=__syscall(SYS_dup2, op->srcfd, op->fd))<0)
-+ if ((ret=__sys_dup2(op->srcfd, op->fd))<0)
- goto fail;
- break;
- case FDOP_OPEN:
-- fd = __syscall(SYS_open, op->path,
-- op->oflag | O_LARGEFILE, op->mode);
-+ fd = __sys_open(op->path, op->oflag, op->mode);
- if ((ret=fd) < 0) goto fail;
- if (fd != op->fd) {
-- if ((ret=__syscall(SYS_dup2, fd, op->fd))<0)
-+ if ((ret=__sys_dup2(fd, op->fd))<0)
- goto fail;
- __syscall(SYS_close, fd);
- }
-diff --git a/src/process/vfork.c b/src/process/vfork.c
-index fc4adb4..ac95465 100644
---- a/src/process/vfork.c
-+++ b/src/process/vfork.c
-@@ -1,12 +1,17 @@
- #define _GNU_SOURCE
- #include <unistd.h>
-+#include <signal.h>
- #include "syscall.h"
- #include "libc.h"
-
- pid_t __vfork(void)
- {
- /* vfork syscall cannot be made from C code */
-+#ifdef SYS_fork
- return syscall(SYS_fork);
-+#else
-+ return syscall(SYS_clone, SIGCHLD, 0);
-+#endif
- }
-
- weak_alias(__vfork, vfork);
-diff --git a/src/select/poll.c b/src/select/poll.c
-index f1e73e8..9e0bcbd 100644
---- a/src/select/poll.c
-+++ b/src/select/poll.c
-@@ -1,8 +1,16 @@
- #include <poll.h>
-+#include <time.h>
-+#include <signal.h>
- #include "syscall.h"
- #include "libc.h"
-
- int poll(struct pollfd *fds, nfds_t n, int timeout)
- {
-+#ifdef SYS_poll
- return syscall_cp(SYS_poll, fds, n, timeout);
-+#else
-+ return syscall_cp(SYS_ppoll, fds, n, timeout>=0 ?
-+ &((struct timespec){ .tv_sec = timeout/1000,
-+ .tv_nsec = timeout%1000*1000000 }) : 0, 0, _NSIG/8);
-+#endif
- }
-diff --git a/src/select/pselect.c b/src/select/pselect.c
-index a19e153..4e2d7b0 100644
---- a/src/select/pselect.c
-+++ b/src/select/pselect.c
-@@ -1,11 +1,12 @@
- #include <sys/select.h>
- #include <signal.h>
-+#include <stdint.h>
- #include "syscall.h"
- #include "libc.h"
-
- int pselect(int n, fd_set *restrict rfds, fd_set *restrict wfds, fd_set *restrict efds, const struct timespec *restrict ts, const sigset_t *restrict mask)
- {
-- long data[2] = { (long)mask, _NSIG/8 };
-+ syscall_arg_t data[2] = { (uintptr_t)mask, _NSIG/8 };
- struct timespec ts_tmp;
- if (ts) ts_tmp = *ts;
- return syscall_cp(SYS_pselect6, n, rfds, wfds, efds, ts ? &ts_tmp : 0, data);
-diff --git a/src/select/select.c b/src/select/select.c
-index f93597b..7b5f6dc 100644
---- a/src/select/select.c
-+++ b/src/select/select.c
-@@ -1,8 +1,26 @@
- #include <sys/select.h>
-+#include <signal.h>
-+#include <stdint.h>
-+#include <errno.h>
- #include "syscall.h"
- #include "libc.h"
-
- int select(int n, fd_set *restrict rfds, fd_set *restrict wfds, fd_set *restrict efds, struct timeval *restrict tv)
- {
-+#ifdef SYS_select
- return syscall_cp(SYS_select, n, rfds, wfds, efds, tv);
-+#else
-+ syscall_arg_t data[2] = { 0, _NSIG/8 };
-+ struct timespec ts;
-+ if (tv) {
-+ if (tv->tv_sec < 0 || tv->tv_usec < 0)
-+ return __syscall_ret(-EINVAL);
-+ time_t extra_secs = tv->tv_usec / 1000000;
-+ ts.tv_nsec = tv->tv_usec % 1000000 * 1000;
-+ const time_t max_time = (1ULL<<8*sizeof(time_t)-1)-1;
-+ ts.tv_sec = extra_secs > max_time - tv->tv_sec ?
-+ max_time : tv->tv_sec + extra_secs;
-+ }
-+ return syscall_cp(SYS_pselect6, n, rfds, wfds, efds, tv ? &ts : 0, data);
-+#endif
- }
-diff --git a/src/stat/chmod.c b/src/stat/chmod.c
-index beb66e5..d4f53c5 100644
---- a/src/stat/chmod.c
-+++ b/src/stat/chmod.c
-@@ -1,7 +1,12 @@
- #include <sys/stat.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int chmod(const char *path, mode_t mode)
- {
-+#ifdef SYS_chmod
- return syscall(SYS_chmod, path, mode);
-+#else
-+ return syscall(SYS_fchmodat, AT_FDCWD, path, mode);
-+#endif
- }
-diff --git a/src/stat/fchmod.c b/src/stat/fchmod.c
-index 6d28141..93e1b64 100644
---- a/src/stat/fchmod.c
-+++ b/src/stat/fchmod.c
-@@ -13,5 +13,9 @@ int fchmod(int fd, mode_t mode)
-
- char buf[15+3*sizeof(int)];
- __procfdname(buf, fd);
-+#ifdef SYS_chmod
- return syscall(SYS_chmod, buf, mode);
-+#else
-+ return syscall(SYS_fchmodat, AT_FDCWD, buf, mode);
-+#endif
- }
-diff --git a/src/stat/fchmodat.c b/src/stat/fchmodat.c
-index 12e7ff0..afa6d44 100644
---- a/src/stat/fchmodat.c
-+++ b/src/stat/fchmodat.c
-@@ -28,8 +28,9 @@ int fchmodat(int fd, const char *path, mode_t mode, int flag)
- }
-
- __procfdname(proc, fd2);
-- if (!(ret = __syscall(SYS_stat, proc, &st)) && !S_ISLNK(st.st_mode))
-- ret = __syscall(SYS_chmod, proc, mode);
-+ ret = __syscall(SYS_fstatat, AT_FDCWD, proc, &st, 0);
-+ if (!ret && !S_ISLNK(st.st_mode))
-+ ret = __syscall(SYS_fchmodat, AT_FDCWD, proc, mode);
-
- __syscall(SYS_close, fd2);
- return __syscall_ret(ret);
-diff --git a/src/stat/fstat.c b/src/stat/fstat.c
-index b561176..a928986 100644
---- a/src/stat/fstat.c
-+++ b/src/stat/fstat.c
-@@ -14,7 +14,11 @@ int fstat(int fd, struct stat *st)
-
- char buf[15+3*sizeof(int)];
- __procfdname(buf, fd);
-+#ifdef SYS_stat
- return syscall(SYS_stat, buf, st);
-+#else
-+ return syscall(SYS_fstatat, AT_FDCWD, buf, st);
-+#endif
- }
-
- LFS64(fstat);
-diff --git a/src/stat/futimesat.c b/src/stat/futimesat.c
-index dbefc84..b4eea1d 100644
---- a/src/stat/futimesat.c
-+++ b/src/stat/futimesat.c
-@@ -1,10 +1,23 @@
- #define _GNU_SOURCE
- #include <sys/time.h>
-+#include <sys/stat.h>
-+#include <errno.h>
- #include "syscall.h"
-+#include "libc.h"
-
--#ifdef SYS_futimesat
--int futimesat(int dirfd, const char *pathname, const struct timeval times[2])
-+int __futimesat(int dirfd, const char *pathname, const struct timeval times[2])
- {
-- return syscall(SYS_futimesat, dirfd, pathname, times);
-+ struct timespec ts[2];
-+ if (times) {
-+ int i;
-+ for (i=0; i<2; i++) {
-+ if (times[i].tv_usec >= 1000000ULL)
-+ return __syscall_ret(-EINVAL);
-+ ts[i].tv_sec = times[i].tv_sec;
-+ ts[i].tv_nsec = times[i].tv_usec * 1000;
-+ }
-+ }
-+ return utimensat(dirfd, pathname, times ? ts : 0, 0);
- }
--#endif
-+
-+weak_alias(__futimesat, futimesat);
-diff --git a/src/stat/lstat.c b/src/stat/lstat.c
-index 8f60358..5e8b84f 100644
---- a/src/stat/lstat.c
-+++ b/src/stat/lstat.c
-@@ -1,10 +1,15 @@
- #include <sys/stat.h>
-+#include <fcntl.h>
- #include "syscall.h"
- #include "libc.h"
-
- int lstat(const char *restrict path, struct stat *restrict buf)
- {
-+#ifdef SYS_lstat
- return syscall(SYS_lstat, path, buf);
-+#else
-+ return syscall(SYS_fstatat, AT_FDCWD, path, buf, AT_SYMLINK_NOFOLLOW);
-+#endif
- }
-
- LFS64(lstat);
-diff --git a/src/stat/mkdir.c b/src/stat/mkdir.c
-index 770e1cc..32625b7 100644
---- a/src/stat/mkdir.c
-+++ b/src/stat/mkdir.c
-@@ -1,7 +1,12 @@
- #include <sys/stat.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int mkdir(const char *path, mode_t mode)
- {
-+#ifdef SYS_mkdir
- return syscall(SYS_mkdir, path, mode);
-+#else
-+ return syscall(SYS_mkdirat, AT_FDCWD, path, mode);
-+#endif
- }
-diff --git a/src/stat/mknod.c b/src/stat/mknod.c
-index c319657..beebd84 100644
---- a/src/stat/mknod.c
-+++ b/src/stat/mknod.c
-@@ -1,7 +1,12 @@
- #include <sys/stat.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int mknod(const char *path, mode_t mode, dev_t dev)
- {
-+#ifdef SYS_mknod
- return syscall(SYS_mknod, path, mode, dev);
-+#else
-+ return syscall(SYS_mknodat, AT_FDCWD, path, mode, dev);
-+#endif
- }
-diff --git a/src/stat/stat.c b/src/stat/stat.c
-index c6de716..b4433a0 100644
---- a/src/stat/stat.c
-+++ b/src/stat/stat.c
-@@ -1,10 +1,15 @@
- #include <sys/stat.h>
-+#include <fcntl.h>
- #include "syscall.h"
- #include "libc.h"
-
- int stat(const char *restrict path, struct stat *restrict buf)
- {
-+#ifdef SYS_stat
- return syscall(SYS_stat, path, buf);
-+#else
-+ return syscall(SYS_fstatat, AT_FDCWD, path, buf, 0);
-+#endif
- }
-
- LFS64(stat);
-diff --git a/src/stat/utimensat.c b/src/stat/utimensat.c
-index 929698b..159c8be 100644
---- a/src/stat/utimensat.c
-+++ b/src/stat/utimensat.c
-@@ -1,7 +1,37 @@
- #include <sys/stat.h>
-+#include <sys/time.h>
-+#include <fcntl.h>
-+#include <errno.h>
- #include "syscall.h"
-
- int utimensat(int fd, const char *path, const struct timespec times[2], int flags)
- {
-- return syscall(SYS_utimensat, fd, path, times, flags);
-+ int r = __syscall(SYS_utimensat, fd, path, times, flags);
-+#ifdef SYS_futimesat
-+ if (r != -ENOSYS || flags) return __syscall_ret(r);
-+ struct timeval *tv = 0, tmp[2];
-+ if (times) {
-+ int i;
-+ tv = tmp;
-+ for (i=0; i<2; i++) {
-+ if (times[i].tv_nsec >= 1000000000ULL) {
-+ if (times[i].tv_nsec == UTIME_NOW &&
-+ times[1-i].tv_nsec == UTIME_NOW) {
-+ tv = 0;
-+ break;
-+ }
-+ if (times[i].tv_nsec == UTIME_OMIT)
-+ return __syscall_ret(-ENOSYS);
-+ return __syscall_ret(-EINVAL);
-+ }
-+ tmp[i].tv_sec = times[i].tv_sec;
-+ tmp[i].tv_usec = times[i].tv_nsec / 1000;
-+ }
-+ }
-+
-+ r = __syscall(SYS_futimesat, fd, path, tv);
-+ if (r != -ENOSYS || fd != AT_FDCWD) return __syscall_ret(r);
-+ r = __syscall(SYS_utimes, path, tv);
-+#endif
-+ return __syscall_ret(r);
- }
-diff --git a/src/stdio/__fopen_rb_ca.c b/src/stdio/__fopen_rb_ca.c
-index 9202c8c..b72c630 100644
---- a/src/stdio/__fopen_rb_ca.c
-+++ b/src/stdio/__fopen_rb_ca.c
-@@ -6,7 +6,7 @@ FILE *__fopen_rb_ca(const char *filename, FILE *f, unsigned char *buf, size_t le
- {
- memset(f, 0, sizeof *f);
-
-- f->fd = syscall(SYS_open, filename, O_RDONLY|O_LARGEFILE|O_CLOEXEC, 0);
-+ f->fd = sys_open(filename, O_RDONLY|O_CLOEXEC);
- if (f->fd < 0) return 0;
-
- f->flags = F_NOWR | F_PERM;
-diff --git a/src/stdio/fopen.c b/src/stdio/fopen.c
-index da17ce8..3d97cfa 100644
---- a/src/stdio/fopen.c
-+++ b/src/stdio/fopen.c
-@@ -18,7 +18,7 @@ FILE *fopen(const char *restrict filename, const char *restrict mode)
- /* Compute the flags to pass to open() */
- flags = __fmodeflags(mode);
-
-- fd = syscall_cp(SYS_open, filename, flags|O_LARGEFILE, 0666);
-+ fd = sys_open_cp(filename, flags, 0666);
- if (fd < 0) return 0;
-
- f = __fdopen(fd, mode);
-diff --git a/src/stdio/remove.c b/src/stdio/remove.c
-index e147ba2..942e301 100644
---- a/src/stdio/remove.c
-+++ b/src/stdio/remove.c
-@@ -1,9 +1,19 @@
- #include <stdio.h>
- #include <errno.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int remove(const char *path)
- {
-- int r = syscall(SYS_unlink, path);
-- return (r && errno == EISDIR) ? syscall(SYS_rmdir, path) : r;
-+#ifdef SYS_unlink
-+ int r = __syscall(SYS_unlink, path);
-+#else
-+ int r = __syscall(SYS_unlinkat, AT_FDCWD, path, 0);
-+#endif
-+#ifdef SYS_rmdir
-+ if (r==-EISDIR) r = __syscall(SYS_rmdir, path);
-+#else
-+ if (r==-EISDIR) r = __syscall(SYS_unlinkat, AT_FDCWD, path, AT_REMOVEDIR);
-+#endif
-+ return __syscall_ret(r);
- }
-diff --git a/src/stdio/rename.c b/src/stdio/rename.c
-index 97f1453..04c90c0 100644
---- a/src/stdio/rename.c
-+++ b/src/stdio/rename.c
-@@ -1,7 +1,12 @@
- #include <stdio.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int rename(const char *old, const char *new)
- {
-+#ifdef SYS_rename
- return syscall(SYS_rename, old, new);
-+#else
-+ return syscall(SYS_renameat, AT_FDCWD, old, AT_FDCWD, new);
-+#endif
- }
-diff --git a/src/stdio/tempnam.c b/src/stdio/tempnam.c
-index f73ca9f..45a5f26 100644
---- a/src/stdio/tempnam.c
-+++ b/src/stdio/tempnam.c
-@@ -1,42 +1,48 @@
- #include <stdio.h>
-+#include <fcntl.h>
-+#include <errno.h>
-+#include <sys/stat.h>
-+#include <limits.h>
- #include <string.h>
--#include <stdlib.h>
--#include <stdint.h>
--#include <unistd.h>
--#include <time.h>
--#include "libc.h"
--#include "atomic.h"
-+#include "syscall.h"
-
- #define MAXTRIES 100
-
-+char *__randname(char *);
-+
- char *tempnam(const char *dir, const char *pfx)
- {
-- static int index;
-- char *s;
-- struct timespec ts;
-- int pid = getpid();
-- size_t l;
-- int n;
-- int try=0;
-+ char s[PATH_MAX];
-+ size_t l, dl, pl;
-+ int try;
-+ int r;
-
- if (!dir) dir = P_tmpdir;
- if (!pfx) pfx = "temp";
-
-- if (access(dir, R_OK|W_OK|X_OK) != 0)
-- return NULL;
--
-- l = strlen(dir) + 1 + strlen(pfx) + 3*(sizeof(int)*3+2) + 1;
-- s = malloc(l);
-- if (!s) return s;
-+ dl = strlen(dir);
-+ pl = strlen(pfx);
-+ l = dl + 1 + pl + 1 + 6;
-
-- do {
-- clock_gettime(CLOCK_REALTIME, &ts);
-- n = ts.tv_nsec ^ (uintptr_t)&s ^ (uintptr_t)s;
-- snprintf(s, l, "%s/%s-%d-%d-%x", dir, pfx, pid, a_fetch_add(&index, 1), n);
-- } while (!access(s, F_OK) && try++<MAXTRIES);
-- if (try>=MAXTRIES) {
-- free(s);
-+ if (l >= PATH_MAX) {
-+ errno = ENAMETOOLONG;
- return 0;
- }
-- return s;
-+
-+ memcpy(s, dir, dl);
-+ s[dl] = '/';
-+ memcpy(s+dl+1, pfx, pl);
-+ s[dl+1+pl] = '_';
-+
-+ for (try=0; try<MAXTRIES; try++) {
-+ __randname(s+l-6);
-+#ifdef SYS_lstat
-+ r = __syscall(SYS_lstat, s, &(struct stat){0});
-+#else
-+ r = __syscall(SYS_fstatat, AT_FDCWD, s,
-+ &(struct stat){0}, AT_SYMLINK_NOFOLLOW);
-+#endif
-+ if (r == -ENOENT) return strdup(s);
-+ }
-+ return 0;
- }
-diff --git a/src/stdio/tmpfile.c b/src/stdio/tmpfile.c
-index 926d660..a7d0000 100644
---- a/src/stdio/tmpfile.c
-+++ b/src/stdio/tmpfile.c
-@@ -1,23 +1,27 @@
- #include <stdio.h>
- #include <fcntl.h>
--#include <unistd.h>
- #include "stdio_impl.h"
-
- #define MAXTRIES 100
-
-+char *__randname(char *);
-+
- FILE *tmpfile(void)
- {
-- char buf[L_tmpnam], *s;
-+ char s[] = "/tmp/tmpfile_XXXXXX";
- int fd;
- FILE *f;
- int try;
- for (try=0; try<MAXTRIES; try++) {
-- s = tmpnam(buf);
-- if (!s) return 0;
-- fd = syscall(SYS_open, s, O_RDWR|O_CREAT|O_EXCL|O_LARGEFILE, 0600);
-+ __randname(s+13);
-+ fd = sys_open(s, O_RDWR|O_CREAT|O_EXCL, 0600);
- if (fd >= 0) {
- f = __fdopen(fd, "w+");
-+#ifdef SYS_unlink
- __syscall(SYS_unlink, s);
-+#else
-+ __syscall(SYS_unlinkat, AT_FDCWD, s, 0);
-+#endif
- return f;
- }
- }
-diff --git a/src/stdio/tmpnam.c b/src/stdio/tmpnam.c
-index 2bd72b3..449eb9b 100644
---- a/src/stdio/tmpnam.c
-+++ b/src/stdio/tmpnam.c
-@@ -1,31 +1,29 @@
- #include <stdio.h>
--#include <stdlib.h>
--#include <stdint.h>
--#include <unistd.h>
--#include <time.h>
--#include "libc.h"
-+#include <fcntl.h>
-+#include <errno.h>
-+#include <sys/stat.h>
-+#include <string.h>
- #include "syscall.h"
--#include "atomic.h"
-
- #define MAXTRIES 100
-
--char *tmpnam(char *s)
--{
-- static int index;
-- static char s2[L_tmpnam];
-- struct timespec ts;
-- int try = 0;
-- unsigned n;
--
-- if (!s) s = s2;
-+char *__randname(char *);
-
-- if (__syscall(SYS_access, P_tmpdir, R_OK|W_OK|X_OK) != 0)
-- return NULL;
--
-- do {
-- __syscall(SYS_clock_gettime, CLOCK_REALTIME, &ts, 0);
-- n = ts.tv_nsec ^ (uintptr_t)&s ^ (uintptr_t)s;
-- snprintf(s, L_tmpnam, "/tmp/t%x-%x", a_fetch_add(&index, 1), n);
-- } while (!__syscall(SYS_access, s, F_OK) && try++<MAXTRIES);
-- return try>=MAXTRIES ? 0 : s;
-+char *tmpnam(char *buf)
-+{
-+ static char internal[L_tmpnam];
-+ char s[] = "/tmp/tmpnam_XXXXXX";
-+ int try;
-+ int r;
-+ for (try=0; try<MAXTRIES; try++) {
-+ __randname(s+12);
-+#ifdef SYS_lstat
-+ r = __syscall(SYS_lstat, s, &(struct stat){0});
-+#else
-+ r = __syscall(SYS_fstatat, AT_FDCWD, s,
-+ &(struct stat){0}, AT_SYMLINK_NOFOLLOW);
-+#endif
-+ if (r == -ENOENT) return strcpy(buf ? buf : internal, s);
-+ }
-+ return 0;
- }
-diff --git a/src/stdio/vfprintf.c b/src/stdio/vfprintf.c
-index f6e7f38..ea25772 100644
---- a/src/stdio/vfprintf.c
-+++ b/src/stdio/vfprintf.c
-@@ -13,8 +13,6 @@
-
- #define MAX(a,b) ((a)>(b) ? (a) : (b))
- #define MIN(a,b) ((a)<(b) ? (a) : (b))
--#define CONCAT2(x,y) x ## y
--#define CONCAT(x,y) CONCAT2(x,y)
-
- /* Convenient bit representation for modifier flags, which all fall
- * within 31 codepoints of the space character. */
-@@ -343,7 +341,7 @@ static int fmt_fp(FILE *f, long double y, int w, int p, int fl, int t)
- x = *d % i;
- /* Are there any significant digits past j? */
- if (x || d+1!=z) {
-- long double round = CONCAT(0x1p,LDBL_MANT_DIG);
-+ long double round = 2/LDBL_EPSILON;
- long double small;
- if (*d/i & 1) round += 2;
- if (x<i/2) small=0x0.8p0;
-diff --git a/src/time/__map_file.c b/src/time/__map_file.c
-index 84ae839..d06a581 100644
---- a/src/time/__map_file.c
-+++ b/src/time/__map_file.c
-@@ -9,8 +9,7 @@ const char unsigned *__map_file(const char *pathname, size_t *size)
- {
- struct stat st;
- const unsigned char *map = MAP_FAILED;
-- int flags = O_RDONLY|O_LARGEFILE|O_CLOEXEC|O_NONBLOCK;
-- int fd = __syscall(SYS_open, pathname, flags);
-+ int fd = __sys_open(pathname, O_RDONLY|O_CLOEXEC|O_NONBLOCK);
- if (fd < 0) return 0;
- if (!__syscall(SYS_fstat, fd, &st))
- map = __mmap(0, st.st_size, PROT_READ, MAP_SHARED, fd, 0);
-diff --git a/src/time/utime.c b/src/time/utime.c
-index b2b5741..e7592b2 100644
---- a/src/time/utime.c
-+++ b/src/time/utime.c
-@@ -1,14 +1,11 @@
- #include <utime.h>
--#include <sys/time.h>
--#include "syscall.h"
-+#include <sys/stat.h>
-+#include <time.h>
-+#include <fcntl.h>
-
- int utime(const char *path, const struct utimbuf *times)
- {
-- if (times) {
-- struct timeval tv[2] = {
-- { .tv_sec = times->actime },
-- { .tv_sec = times->modtime } };
-- return syscall(SYS_utimes, path, tv);
-- }
-- return syscall(SYS_utimes, path, 0);
-+ return utimensat(AT_FDCWD, path, times ? ((struct timespec [2]){
-+ { .tv_sec = times->actime }, { .tv_sec = times->modtime }})
-+ : 0, 0);
- }
-diff --git a/src/unistd/access.c b/src/unistd/access.c
-index e7ce73a..d6eed68 100644
---- a/src/unistd/access.c
-+++ b/src/unistd/access.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int access(const char *filename, int amode)
- {
-+#ifdef SYS_access
- return syscall(SYS_access, filename, amode);
-+#else
-+ return syscall(SYS_faccessat, AT_FDCWD, filename, amode, 0);
-+#endif
- }
-diff --git a/src/unistd/chown.c b/src/unistd/chown.c
-index 95f6f61..14b0325 100644
---- a/src/unistd/chown.c
-+++ b/src/unistd/chown.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int chown(const char *path, uid_t uid, gid_t gid)
- {
-+#ifdef SYS_chown
- return syscall(SYS_chown, path, uid, gid);
-+#else
-+ return syscall(SYS_fchownat, AT_FDCWD, path, uid, gid, 0);
-+#endif
- }
-diff --git a/src/unistd/dup2.c b/src/unistd/dup2.c
-index 87a0d44..8f43c6d 100644
---- a/src/unistd/dup2.c
-+++ b/src/unistd/dup2.c
-@@ -1,10 +1,20 @@
- #include <unistd.h>
- #include <errno.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int dup2(int old, int new)
- {
- int r;
-+#ifdef SYS_dup2
- while ((r=__syscall(SYS_dup2, old, new))==-EBUSY);
-+#else
-+ if (old==new) {
-+ r = __syscall(SYS_fcntl, old, F_GETFD);
-+ if (r >= 0) return old;
-+ } else {
-+ while ((r=__syscall(SYS_dup3, old, new, 0))==-EBUSY);
-+ }
-+#endif
- return __syscall_ret(r);
- }
-diff --git a/src/unistd/dup3.c b/src/unistd/dup3.c
-index 1f7134b..0eb6caf 100644
---- a/src/unistd/dup3.c
-+++ b/src/unistd/dup3.c
-@@ -8,6 +8,7 @@
- int __dup3(int old, int new, int flags)
- {
- int r;
-+#ifdef SYS_dup2
- if (old==new) return __syscall_ret(-EINVAL);
- if (flags & O_CLOEXEC) {
- while ((r=__syscall(SYS_dup3, old, new, flags))==-EBUSY);
-@@ -15,6 +16,9 @@ int __dup3(int old, int new, int flags)
- }
- while ((r=__syscall(SYS_dup2, old, new))==-EBUSY);
- if (flags & O_CLOEXEC) __syscall(SYS_fcntl, new, F_SETFD, FD_CLOEXEC);
-+#else
-+ while ((r=__syscall(SYS_dup3, old, new, flags))==-EBUSY);
-+#endif
- return __syscall_ret(r);
- }
-
-diff --git a/src/unistd/fchown.c b/src/unistd/fchown.c
-index 36633b0..0345984 100644
---- a/src/unistd/fchown.c
-+++ b/src/unistd/fchown.c
-@@ -13,5 +13,10 @@ int fchown(int fd, uid_t uid, gid_t gid)
-
- char buf[15+3*sizeof(int)];
- __procfdname(buf, fd);
-+#ifdef SYS_chown
- return syscall(SYS_chown, buf, uid, gid);
-+#else
-+ return syscall(SYS_fchownat, AT_FDCWD, buf, uid, gid);
-+#endif
-+
- }
-diff --git a/src/unistd/getpgrp.c b/src/unistd/getpgrp.c
-index 433f42e..90e9bb0 100644
---- a/src/unistd/getpgrp.c
-+++ b/src/unistd/getpgrp.c
-@@ -3,5 +3,5 @@
-
- pid_t getpgrp(void)
- {
-- return __syscall(SYS_getpgrp);
-+ return __syscall(SYS_getpgid, 0);
- }
-diff --git a/src/unistd/lchown.c b/src/unistd/lchown.c
-index de871ae..ccd5ee0 100644
---- a/src/unistd/lchown.c
-+++ b/src/unistd/lchown.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int lchown(const char *path, uid_t uid, gid_t gid)
- {
-+#ifdef SYS_lchown
- return syscall(SYS_lchown, path, uid, gid);
-+#else
-+ return syscall(SYS_fchownat, AT_FDCWD, path, uid, gid, AT_SYMLINK_NOFOLLOW);
-+#endif
- }
-diff --git a/src/unistd/link.c b/src/unistd/link.c
-index 20193f2..feec18e 100644
---- a/src/unistd/link.c
-+++ b/src/unistd/link.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int link(const char *existing, const char *new)
- {
-+#ifdef SYS_link
- return syscall(SYS_link, existing, new);
-+#else
-+ return syscall(SYS_linkat, AT_FDCWD, existing, AT_FDCWD, new, 0);
-+#endif
- }
-diff --git a/src/unistd/pause.c b/src/unistd/pause.c
-index f7ed17d..56eb171 100644
---- a/src/unistd/pause.c
-+++ b/src/unistd/pause.c
-@@ -1,8 +1,13 @@
- #include <unistd.h>
-+#include <signal.h>
- #include "syscall.h"
- #include "libc.h"
-
- int pause(void)
- {
-+#ifdef SYS_pause
- return syscall_cp(SYS_pause);
-+#else
-+ return syscall_cp(SYS_ppoll, 0, 0, 0, 0);
-+#endif
- }
-diff --git a/src/unistd/pipe.c b/src/unistd/pipe.c
-index 36c6f13..d07b8d2 100644
---- a/src/unistd/pipe.c
-+++ b/src/unistd/pipe.c
-@@ -3,5 +3,9 @@
-
- int pipe(int fd[2])
- {
-+#ifdef SYS_pipe
- return syscall(SYS_pipe, fd);
-+#else
-+ return syscall(SYS_pipe2, fd, 0);
-+#endif
- }
-diff --git a/src/unistd/readlink.c b/src/unistd/readlink.c
-index ec291e3..a152d52 100644
---- a/src/unistd/readlink.c
-+++ b/src/unistd/readlink.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- ssize_t readlink(const char *restrict path, char *restrict buf, size_t bufsize)
- {
-+#ifdef SYS_readlink
- return syscall(SYS_readlink, path, buf, bufsize);
-+#else
-+ return syscall(SYS_readlinkat, AT_FDCWD, path, buf, bufsize);
-+#endif
- }
-diff --git a/src/unistd/rmdir.c b/src/unistd/rmdir.c
-index dfe1605..6825ffc 100644
---- a/src/unistd/rmdir.c
-+++ b/src/unistd/rmdir.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int rmdir(const char *path)
- {
-+#ifdef SYS_rmdir
- return syscall(SYS_rmdir, path);
-+#else
-+ return syscall(SYS_unlinkat, AT_FDCWD, path, AT_REMOVEDIR);
-+#endif
- }
-diff --git a/src/unistd/symlink.c b/src/unistd/symlink.c
-index 5902d45..0973d78 100644
---- a/src/unistd/symlink.c
-+++ b/src/unistd/symlink.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int symlink(const char *existing, const char *new)
- {
-+#ifdef SYS_symlink
- return syscall(SYS_symlink, existing, new);
-+#else
-+ return syscall(SYS_symlinkat, existing, AT_FDCWD, new);
-+#endif
- }
-diff --git a/src/unistd/unlink.c b/src/unistd/unlink.c
-index bdb37be..c40c28d 100644
---- a/src/unistd/unlink.c
-+++ b/src/unistd/unlink.c
-@@ -1,7 +1,12 @@
- #include <unistd.h>
-+#include <fcntl.h>
- #include "syscall.h"
-
- int unlink(const char *path)
- {
-+#ifdef SYS_unlink
- return syscall(SYS_unlink, path);
-+#else
-+ return syscall(SYS_unlinkat, AT_FDCWD, path, 0);
-+#endif
- }
diff --git a/main/musl/0002-76f440cf-to-d85d261e.patch b/main/musl/0002-76f440cf-to-d85d261e.patch
deleted file mode 100644
index 67e2e46ed..000000000
--- a/main/musl/0002-76f440cf-to-d85d261e.patch
+++ /dev/null
@@ -1,89 +0,0 @@
-diff --git a/src/multibyte/wcsrtombs.c b/src/multibyte/wcsrtombs.c
-index 5cf8f3e..30be415 100644
---- a/src/multibyte/wcsrtombs.c
-+++ b/src/multibyte/wcsrtombs.c
-@@ -21,8 +21,13 @@ size_t wcsrtombs(char *restrict s, const wchar_t **restrict ws, size_t n, mbstat
- }
- return n;
- }
-- while (n>=4 && **ws) {
-- if (**ws >= 0x80u) {
-+ while (n>=4) {
-+ if (**ws-1u >= 0x7fu) {
-+ if (!**ws) {
-+ *s = 0;
-+ *ws = 0;
-+ return N-n;
-+ }
- l = wcrtomb(s, **ws, 0);
- if (!(l+1)) return -1;
- s += l;
-@@ -33,8 +38,13 @@ size_t wcsrtombs(char *restrict s, const wchar_t **restrict ws, size_t n, mbstat
- }
- (*ws)++;
- }
-- while (n && **ws) {
-- if (**ws >= 0x80u) {
-+ while (n) {
-+ if (**ws-1u >= 0x7fu) {
-+ if (!**ws) {
-+ *s = 0;
-+ *ws = 0;
-+ return N-n;
-+ }
- l = wcrtomb(buf, **ws, 0);
- if (!(l+1)) return -1;
- if (l>n) return N-n;
-@@ -47,7 +57,5 @@ size_t wcsrtombs(char *restrict s, const wchar_t **restrict ws, size_t n, mbstat
- }
- (*ws)++;
- }
-- if (n) *s = 0;
-- *ws = 0;
-- return N-n;
-+ return N;
- }
-diff --git a/src/network/dns_parse.c b/src/network/dns_parse.c
-index aa0d39f..0c7a601 100644
---- a/src/network/dns_parse.c
-+++ b/src/network/dns_parse.c
-@@ -6,6 +6,7 @@ int __dns_parse(const unsigned char *r, int rlen, int (*callback)(void *, int, c
- const unsigned char *p;
- int len;
-
-+ if (rlen<12) return -1;
- if ((r[3]&15)) return 0;
- p = r+12;
- qdcount = r[4]*256 + r[5];
-@@ -13,13 +14,13 @@ int __dns_parse(const unsigned char *r, int rlen, int (*callback)(void *, int, c
- if (qdcount+ancount > 64) return -1;
- while (qdcount--) {
- while (p-r < rlen && *p-1U < 127) p++;
-- if (*p>193 || (*p==193 && p[1]>254) || p>r+506)
-+ if (*p>193 || (*p==193 && p[1]>254) || p>r+rlen-6)
- return -1;
- p += 5 + !!*p;
- }
- while (ancount--) {
- while (p-r < rlen && *p-1U < 127) p++;
-- if (*p>193 || (*p==193 && p[1]>254) || p>r+506)
-+ if (*p>193 || (*p==193 && p[1]>254) || p>r+rlen-6)
- return -1;
- p += 1 + !!*p;
- len = p[8]*256 + p[9];
-diff --git a/src/network/lookup_name.c b/src/network/lookup_name.c
-index 8d41627..0292093 100644
---- a/src/network/lookup_name.c
-+++ b/src/network/lookup_name.c
-@@ -151,7 +151,10 @@ static int name_from_dns(struct address buf[static MAXADDRS], char canon[static
- for (i=0; i<nq; i++)
- __dns_parse(abuf[i], alens[i], dns_parse_callback, &ctx);
-
-- return ctx.cnt;
-+ if (ctx.cnt) return ctx.cnt;
-+ if (alens[0] < 4 || (abuf[0][3] & 15) == 2) return EAI_AGAIN;
-+ if ((abuf[0][3] & 15) == 3) return EAI_NONAME;
-+ return EAI_FAIL;
- }
-
- int __lookup_name(struct address buf[static MAXADDRS], char canon[static 256], const char *name, int family, int flags)
diff --git a/main/musl/0003-d85d261e-to-2abb70c3.patch b/main/musl/0003-d85d261e-to-2abb70c3.patch
deleted file mode 100644
index 0ceecf5eb..000000000
--- a/main/musl/0003-d85d261e-to-2abb70c3.patch
+++ /dev/null
@@ -1,540 +0,0 @@
-diff --git a/include/netdb.h b/include/netdb.h
-index dfc70e2..703a4b2 100644
---- a/include/netdb.h
-+++ b/include/netdb.h
-@@ -41,7 +41,7 @@ struct addrinfo
- #define NI_NOFQDN 0x04
- #define NI_NAMEREQD 0x08
- #define NI_DGRAM 0x10
--/*#define NI_NUMERICSCOPE */
-+#define NI_NUMERICSCOPE 0x100
-
- #define EAI_BADFLAGS -1
- #define EAI_NONAME -2
-diff --git a/src/network/dn_expand.c b/src/network/dn_expand.c
-index 96adf37..849df19 100644
---- a/src/network/dn_expand.c
-+++ b/src/network/dn_expand.c
-@@ -4,10 +4,11 @@
- int __dn_expand(const unsigned char *base, const unsigned char *end, const unsigned char *src, char *dest, int space)
- {
- const unsigned char *p = src;
-- int len = -1, j;
-- if (space > 256) space = 256;
-+ char *dend = dest + (space > 254 ? 254 : space);
-+ int len = -1, i, j;
- if (p==end || !*p) return -1;
-- for (;;) {
-+ /* detect reference loop using an iteration counter */
-+ for (i=0; i < end-base; i+=2) {
- if (*p & 0xc0) {
- if (p+1==end) return -1;
- j = ((p[0] & 0x3f) << 8) | p[1];
-@@ -16,7 +17,7 @@ int __dn_expand(const unsigned char *base, const unsigned char *end, const unsig
- p = base+j;
- } else if (*p) {
- j = *p+1;
-- if (j>=end-p || j>space) return -1;
-+ if (j>=end-p || j>dend-dest) return -1;
- while (--j) *dest++ = *++p;
- *dest++ = *++p ? '.' : 0;
- } else {
-@@ -24,6 +25,7 @@ int __dn_expand(const unsigned char *base, const unsigned char *end, const unsig
- return len;
- }
- }
-+ return -1;
- }
-
- weak_alias(__dn_expand, dn_expand);
-diff --git a/src/network/ent.c b/src/network/ent.c
-index 4c2f24b..ececdc4 100644
---- a/src/network/ent.c
-+++ b/src/network/ent.c
-@@ -16,11 +16,3 @@ void endhostent(void)
- weak_alias(sethostent, setnetent);
- weak_alias(gethostent, getnetent);
- weak_alias(endhostent, endnetent);
--
--weak_alias(sethostent, setservent);
--weak_alias(gethostent, getservent);
--weak_alias(endhostent, endservent);
--
--weak_alias(sethostent, setprotoent);
--weak_alias(gethostent, getprotoent);
--weak_alias(endhostent, endprotoent);
-diff --git a/src/network/getaddrinfo.c b/src/network/getaddrinfo.c
-index 70b6cfd..d991344 100644
---- a/src/network/getaddrinfo.c
-+++ b/src/network/getaddrinfo.c
-@@ -105,6 +105,7 @@ int getaddrinfo(const char *restrict host, const char *restrict serv, const stru
- case AF_INET6:
- out[k].sa.sin6.sin6_family = AF_INET6;
- out[k].sa.sin6.sin6_port = htons(ports[j].port);
-+ out[k].sa.sin6.sin6_scope_id = addrs[i].scopeid;
- memcpy(&out[k].sa.sin6.sin6_addr, &addrs[i].addr, 16);
- break;
- }
-diff --git a/src/network/getnameinfo.c b/src/network/getnameinfo.c
-index dfcf6ed..588ed76 100644
---- a/src/network/getnameinfo.c
-+++ b/src/network/getnameinfo.c
-@@ -5,6 +5,10 @@
- #include <sys/socket.h>
- #include <netinet/in.h>
- #include <arpa/inet.h>
-+#include <net/if.h>
-+#include <ctype.h>
-+#include "lookup.h"
-+#include "stdio_impl.h"
-
- int __dns_parse(const unsigned char *, int, int (*)(void *, int, const void *, int, const void *), void *);
- int __dn_expand(const unsigned char *, const unsigned char *, const unsigned char *, char *, int);
-@@ -14,6 +18,16 @@ int __res_send(const unsigned char *, int, unsigned char *, int);
- #define PTR_MAX (64 + sizeof ".in-addr.arpa")
- #define RR_PTR 12
-
-+static char *itoa(char *p, unsigned x) {
-+ p += 3*sizeof(int);
-+ *--p = 0;
-+ do {
-+ *--p = '0' + x % 10;
-+ x /= 10;
-+ } while (x);
-+ return p;
-+}
-+
- static void mkptr4(char *s, const unsigned char *ip)
- {
- sprintf(s, "%d.%d.%d.%d.in-addr.arpa",
-@@ -31,6 +45,72 @@ static void mkptr6(char *s, const unsigned char *ip)
- strcpy(s, "ip6.arpa");
- }
-
-+static void reverse_hosts(char *buf, const unsigned char *a, unsigned scopeid, int family)
-+{
-+ char line[512], *p, *z;
-+ unsigned char _buf[1032], atmp[16];
-+ struct address iplit;
-+ FILE _f, *f = __fopen_rb_ca("/etc/hosts", &_f, _buf, sizeof _buf);
-+ if (!f) return;
-+ if (family == AF_INET) {
-+ memcpy(atmp+12, a, 4);
-+ memcpy(atmp, "\0\0\0\0\0\0\0\0\0\0\xff\xff", 12);
-+ a = atmp;
-+ }
-+ while (fgets(line, sizeof line, f)) {
-+ if ((p=strchr(line, '#'))) *p++='\n', *p=0;
-+
-+ for (p=line; *p && !isspace(*p); p++);
-+ *p++ = 0;
-+ if (__lookup_ipliteral(&iplit, line, AF_UNSPEC)<=0)
-+ continue;
-+
-+ if (iplit.family == AF_INET) {
-+ memcpy(iplit.addr+12, iplit.addr, 4);
-+ memcpy(iplit.addr, "\0\0\0\0\0\0\0\0\0\0\xff\xff", 12);
-+ iplit.scopeid = 0;
-+ }
-+
-+ if (memcmp(a, iplit.addr, 16) || iplit.scopeid != scopeid)
-+ continue;
-+
-+ for (; *p && isspace(*p); p++);
-+ for (z=p; *z && !isspace(*z); z++);
-+ *z = 0;
-+ if (z-p < 256) {
-+ memcpy(buf, p, z-p+1);
-+ break;
-+ }
-+ }
-+ __fclose_ca(f);
-+}
-+
-+static void reverse_services(char *buf, int port, int dgram)
-+{
-+ unsigned long svport;
-+ char line[128], *p, *z;
-+ unsigned char _buf[1032];
-+ FILE _f, *f = __fopen_rb_ca("/etc/services", &_f, _buf, sizeof _buf);
-+ if (!f) return;
-+ while (fgets(line, sizeof line, f)) {
-+ if ((p=strchr(line, '#'))) *p++='\n', *p=0;
-+
-+ for (p=line; *p && !isspace(*p); p++);
-+ if (!p) continue;
-+ *p++ = 0;
-+ svport = strtoul(p, &z, 10);
-+
-+ if (svport != port || z==p) continue;
-+ if (dgram && strncmp(z, "/udp", 4)) continue;
-+ if (!dgram && strncmp(z, "/tcp", 4)) continue;
-+ if (p-line > 32) continue;
-+
-+ memcpy(buf, line, p-line);
-+ break;
-+ }
-+ __fclose_ca(f);
-+}
-+
- static int dns_parse_callback(void *c, int rr, const void *data, int len, const void *packet)
- {
- char tmp[256];
-@@ -48,15 +128,17 @@ int getnameinfo(const struct sockaddr *restrict sa, socklen_t sl,
- int flags)
- {
- char ptr[PTR_MAX];
-- char buf[256];
-+ char buf[256], num[3*sizeof(int)+1];
- int af = sa->sa_family;
- unsigned char *a;
-+ unsigned scopeid;
-
- switch (af) {
- case AF_INET:
- a = (void *)&((struct sockaddr_in *)sa)->sin_addr;
- if (sl != sizeof(struct sockaddr_in)) return EAI_FAMILY;
- mkptr4(ptr, a);
-+ scopeid = 0;
- break;
- case AF_INET6:
- a = (void *)&((struct sockaddr_in6 *)sa)->sin6_addr;
-@@ -65,6 +147,7 @@ int getnameinfo(const struct sockaddr *restrict sa, socklen_t sl,
- mkptr6(ptr, a);
- else
- mkptr4(ptr, a+12);
-+ scopeid = ((struct sockaddr_in6 *)sa)->sin6_scope_id;
- break;
- default:
- return EAI_FAMILY;
-@@ -73,6 +156,9 @@ int getnameinfo(const struct sockaddr *restrict sa, socklen_t sl,
- if (node && nodelen) {
- buf[0] = 0;
- if (!(flags & NI_NUMERICHOST)) {
-+ reverse_hosts(buf, a, scopeid, af);
-+ }
-+ if (!*buf && !(flags & NI_NUMERICHOST)) {
- unsigned char query[18+PTR_MAX], reply[512];
- int qlen = __res_mkquery(0, ptr, 1, RR_PTR,
- 0, 0, 0, query, sizeof query);
-@@ -84,16 +170,33 @@ int getnameinfo(const struct sockaddr *restrict sa, socklen_t sl,
- if (!*buf) {
- if (flags & NI_NAMEREQD) return EAI_NONAME;
- inet_ntop(af, a, buf, sizeof buf);
-+ if (scopeid) {
-+ char *p = 0, tmp[IF_NAMESIZE+1];
-+ if (!(flags & NI_NUMERICSCOPE) &&
-+ (IN6_IS_ADDR_LINKLOCAL(a) ||
-+ IN6_IS_ADDR_MC_LINKLOCAL(a)))
-+ p = if_indextoname(scopeid, tmp+1);
-+ if (!p)
-+ p = itoa(num, scopeid);
-+ *--p = '%';
-+ strcat(buf, p);
-+ }
- }
- if (strlen(buf) >= nodelen) return EAI_OVERFLOW;
- strcpy(node, buf);
- }
-
- if (serv && servlen) {
-- if (snprintf(buf, sizeof buf, "%d",
-- ntohs(((struct sockaddr_in *)sa)->sin_port))>=servlen)
-+ char *p = buf;
-+ int port = ntohs(((struct sockaddr_in *)sa)->sin_port);
-+ buf[0] = 0;
-+ if (!(flags & NI_NUMERICSERV))
-+ reverse_services(buf, port, flags & NI_DGRAM);
-+ if (!*p)
-+ p = itoa(num, port);
-+ if (strlen(p) >= servlen)
- return EAI_OVERFLOW;
-- strcpy(serv, buf);
-+ strcpy(serv, p);
- }
-
- return 0;
-diff --git a/src/network/if_nametoindex.c b/src/network/if_nametoindex.c
-index fb4a147..cb6ec05 100644
---- a/src/network/if_nametoindex.c
-+++ b/src/network/if_nametoindex.c
-@@ -14,5 +14,5 @@ unsigned if_nametoindex(const char *name)
- strncpy(ifr.ifr_name, name, sizeof ifr.ifr_name);
- r = ioctl(fd, SIOCGIFINDEX, &ifr);
- __syscall(SYS_close, fd);
-- return r < 0 ? r : ifr.ifr_ifindex;
-+ return r < 0 ? 0 : ifr.ifr_ifindex;
- }
-diff --git a/src/network/lookup.h b/src/network/lookup.h
-index 82c969e..19c9e48 100644
---- a/src/network/lookup.h
-+++ b/src/network/lookup.h
-@@ -22,5 +22,6 @@ struct service {
-
- int __lookup_serv(struct service buf[static MAXSERVS], const char *name, int proto, int flags);
- int __lookup_name(struct address buf[static MAXADDRS], char canon[static 256], const char *name, int family, int flags);
-+int __lookup_ipliteral(struct address buf[static 1], const char *name, int family);
-
- #endif
-diff --git a/src/network/lookup_ipliteral.c b/src/network/lookup_ipliteral.c
-new file mode 100644
-index 0000000..7bcb85f
---- /dev/null
-+++ b/src/network/lookup_ipliteral.c
-@@ -0,0 +1,52 @@
-+#include <sys/socket.h>
-+#include <netinet/in.h>
-+#include <netdb.h>
-+#include <net/if.h>
-+#include <arpa/inet.h>
-+#include <limits.h>
-+#include <stdlib.h>
-+#include <string.h>
-+#include <ctype.h>
-+#include "lookup.h"
-+
-+int __inet_aton(const char *, struct in_addr *);
-+
-+int __lookup_ipliteral(struct address buf[static 1], const char *name, int family)
-+{
-+ struct in_addr a4;
-+ struct in6_addr a6;
-+ if (family != AF_INET6 && __inet_aton(name, &a4)>0) {
-+ memcpy(&buf[0].addr, &a4, sizeof a4);
-+ buf[0].family = AF_INET;
-+ buf[0].scopeid = 0;
-+ return 1;
-+ }
-+ if (family != AF_INET) {
-+ char tmp[64];
-+ char *p = strchr(name, '%'), *z;
-+ unsigned long long scopeid;
-+ if (p && p-name < 64) {
-+ memcpy(tmp, name, p-name);
-+ tmp[p-name] = 0;
-+ name = tmp;
-+ }
-+ if (inet_pton(AF_INET6, name, &a6)<=0) return 0;
-+ memcpy(&buf[0].addr, &a6, sizeof a6);
-+ buf[0].family = AF_INET6;
-+ if (p) {
-+ if (isdigit(*++p)) scopeid = strtoull(p, &z, 10);
-+ else z = p-1;
-+ if (*z) {
-+ if (!IN6_IS_ADDR_LINKLOCAL(&a6) &&
-+ !IN6_IS_ADDR_MC_LINKLOCAL(&a6))
-+ return EAI_NONAME;
-+ scopeid = if_nametoindex(p);
-+ if (!scopeid) return EAI_NONAME;
-+ }
-+ if (scopeid > UINT_MAX) return EAI_NONAME;
-+ buf[0].scopeid = scopeid;
-+ }
-+ return 1;
-+ }
-+ return 0;
-+}
-diff --git a/src/network/lookup_name.c b/src/network/lookup_name.c
-index 0292093..68b172b 100644
---- a/src/network/lookup_name.c
-+++ b/src/network/lookup_name.c
-@@ -1,6 +1,7 @@
- #include <sys/socket.h>
- #include <netinet/in.h>
- #include <netdb.h>
-+#include <net/if.h>
- #include <arpa/inet.h>
- #include <ctype.h>
- #include <stdlib.h>
-@@ -13,7 +14,7 @@
- static int is_valid_hostname(const char *host)
- {
- const unsigned char *s;
-- if (strnlen(host, 256)-1 > 254 || mbstowcs(0, host, 0) > 255) return 0;
-+ if (strnlen(host, 254)-1 >= 253 || mbstowcs(0, host, 0) == -1) return 0;
- for (s=(void *)host; *s>=0x80 || *s=='.' || *s=='-' || isalnum(*s); s++);
- return !*s;
- }
-@@ -36,23 +37,9 @@ static int name_from_null(struct address buf[static 2], const char *name, int fa
- return cnt;
- }
-
--int __inet_aton(const char *, struct in_addr *);
--
- static int name_from_numeric(struct address buf[static 1], const char *name, int family)
- {
-- struct in_addr a4;
-- struct in6_addr a6;
-- if (family != AF_INET6 && __inet_aton(name, &a4)>0) {
-- memcpy(&buf[0].addr, &a4, sizeof a4);
-- buf[0].family = AF_INET;
-- return 1;
-- }
-- if (family != AF_INET && inet_pton(AF_INET6, name, &a6)>0) {
-- memcpy(&buf[0].addr, &a6, sizeof a6);
-- buf[0].family = AF_INET6;
-- return 1;
-- }
-- return 0;
-+ return __lookup_ipliteral(buf, name, family);
- }
-
- static int name_from_hosts(struct address buf[static MAXADDRS], char canon[static 256], const char *name, int family)
-@@ -110,11 +97,13 @@ static int dns_parse_callback(void *c, int rr, const void *data, int len, const
- case RR_A:
- if (len != 4) return -1;
- ctx->addrs[ctx->cnt].family = AF_INET;
-+ ctx->addrs[ctx->cnt].scopeid = 0;
- memcpy(ctx->addrs[ctx->cnt++].addr, data, 4);
- break;
- case RR_AAAA:
- if (len != 16) return -1;
- ctx->addrs[ctx->cnt].family = AF_INET6;
-+ ctx->addrs[ctx->cnt].scopeid = 0;
- memcpy(ctx->addrs[ctx->cnt++].addr, data, 16);
- break;
- case RR_CNAME:
-@@ -164,7 +153,7 @@ int __lookup_name(struct address buf[static MAXADDRS], char canon[static 256], c
- *canon = 0;
- if (name) {
- size_t l;
-- if ((l = strnlen(name, 256))-1 > 254)
-+ if ((l = strnlen(name, 254))-1 >= 253)
- return EAI_NONAME;
- memcpy(canon, name, l+1);
- }
-@@ -179,10 +168,10 @@ int __lookup_name(struct address buf[static MAXADDRS], char canon[static 256], c
-
- /* Try each backend until there's at least one result. */
- cnt = name_from_null(buf, name, family, flags);
-- if (cnt<=0) cnt = name_from_numeric(buf, name, family);
-- if (cnt<=0 && !(flags & AI_NUMERICHOST)) {
-+ if (!cnt) cnt = name_from_numeric(buf, name, family);
-+ if (!cnt && !(flags & AI_NUMERICHOST)) {
- cnt = name_from_hosts(buf, canon, name, family);
-- if (cnt<=0) cnt = name_from_dns(buf, canon, name, family);
-+ if (!cnt) cnt = name_from_dns(buf, canon, name, family);
- }
- if (cnt<=0) return cnt ? cnt : EAI_NONAME;
-
-@@ -204,7 +193,6 @@ int __lookup_name(struct address buf[static MAXADDRS], char canon[static 256], c
- if (buf[i].family != AF_INET) continue;
- memcpy(buf[i].addr+12, buf[i].addr, 4);
- memcpy(buf[i].addr, "\0\0\0\0\0\0\0\0\0\0\xff\xff", 12);
-- buf[i].scopeid = 0;
- buf[i].family = AF_INET6;
- }
- }
-diff --git a/src/network/res_mkquery.c b/src/network/res_mkquery.c
-index f7e4e9c..7c49709 100644
---- a/src/network/res_mkquery.c
-+++ b/src/network/res_mkquery.c
-@@ -10,9 +10,9 @@ int __res_mkquery(int op, const char *dname, int class, int type,
- int id, i, j;
- unsigned char q[280];
- struct timespec ts;
-- size_t l = strnlen(dname, 256);
-+ size_t l = strnlen(dname, 254);
-
-- if (l-1>=254 || buflen<18+l || op>15u || class>255u || type>255u)
-+ if (l-1>=253 || buflen<18+l || op>15u || class>255u || type>255u)
- return -1;
-
- /* Construct query template - ID will be filled later */
-diff --git a/src/network/res_msend.c b/src/network/res_msend.c
-index a5b7793..5192b4d 100644
---- a/src/network/res_msend.c
-+++ b/src/network/res_msend.c
-@@ -12,6 +12,7 @@
- #include <pthread.h>
- #include "stdio_impl.h"
- #include "syscall.h"
-+#include "lookup.h"
-
- static void cleanup(void *p)
- {
-@@ -47,6 +48,7 @@ int __res_msend(int nqueries, const unsigned char *const *queries,
- int cs;
- struct pollfd pfd;
- unsigned long t0, t1, t2;
-+ struct address iplit;
-
- pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &cs);
-
-@@ -76,13 +78,18 @@ int __res_msend(int nqueries, const unsigned char *const *queries,
- for (z=s; *z && !isspace(*z); z++);
- *z=0;
-
-- if (inet_pton(AF_INET, s, &ns[nns].sin.sin_addr)>0) {
-- ns[nns].sin.sin_port = htons(53);
-- ns[nns++].sin.sin_family = AF_INET;
-- } else if (inet_pton(AF_INET6, s, &ns[nns].sin6.sin6_addr)>0) {
-- sl = sizeof sa.sin6;
-- ns[nns].sin6.sin6_port = htons(53);
-- ns[nns++].sin6.sin6_family = family = AF_INET6;
-+ if (__lookup_ipliteral(&iplit, s, AF_UNSPEC)>0) {
-+ if (iplit.family == AF_INET) {
-+ memcpy(&ns[nns].sin.sin_addr, iplit.addr, 4);
-+ ns[nns].sin.sin_port = htons(53);
-+ ns[nns++].sin.sin_family = AF_INET;
-+ } else {
-+ sl = sizeof sa.sin6;
-+ memcpy(&ns[nns].sin6.sin6_addr, iplit.addr, 16);
-+ ns[nns].sin6.sin6_port = htons(53);
-+ ns[nns].sin6.sin6_scope_id = iplit.scopeid;
-+ ns[nns++].sin6.sin6_family = family = AF_INET6;
-+ }
- }
- }
- if (f) __fclose_ca(f);
-diff --git a/src/network/res_querydomain.c b/src/network/res_querydomain.c
-index c746dbe..8ba31f4 100644
---- a/src/network/res_querydomain.c
-+++ b/src/network/res_querydomain.c
-@@ -3,10 +3,10 @@
-
- int res_querydomain(const char *name, const char *domain, int class, int type, unsigned char *dest, int len)
- {
-- char tmp[256];
-- size_t nl = strnlen(name, 256);
-- size_t dl = strnlen(domain, 256);
-- if (nl+dl+1 > 255) return -1;
-+ char tmp[254];
-+ size_t nl = strnlen(name, 254);
-+ size_t dl = strnlen(domain, 254);
-+ if (nl+dl+1 > 253) return -1;
- memcpy(tmp, name, nl);
- tmp[nl] = '.';
- memcpy(tmp+nl+1, domain, dl+1);
-diff --git a/src/stdio/vasprintf.c b/src/stdio/vasprintf.c
-index 68b7246..08251bc 100644
---- a/src/stdio/vasprintf.c
-+++ b/src/stdio/vasprintf.c
-@@ -3,26 +3,13 @@
- #include <stdarg.h>
- #include <stdlib.h>
-
--#define GUESS 240U
--
- int vasprintf(char **s, const char *fmt, va_list ap)
- {
- va_list ap2;
-- char *a;
-- int l=GUESS;
--
-- if (!(a=malloc(GUESS))) return -1;
--
- va_copy(ap2, ap);
-- l=vsnprintf(a, GUESS, fmt, ap2);
-+ int l = vsnprintf(0, 0, fmt, ap2);
- va_end(ap2);
-
-- if (l<GUESS) {
-- char *b = realloc(a, l+1U);
-- *s = b ? b : a;
-- return l;
-- }
-- free(a);
- if (l<0 || !(*s=malloc(l+1U))) return -1;
- return vsnprintf(*s, l+1U, fmt, ap);
- }
diff --git a/main/musl/1003-implement-y-and-C-specifiers-in-strptime.patch b/main/musl/1003-implement-y-and-C-specifiers-in-strptime.patch
deleted file mode 100644
index f8c78a090..000000000
--- a/main/musl/1003-implement-y-and-C-specifiers-in-strptime.patch
+++ /dev/null
@@ -1,64 +0,0 @@
-From c133ba2ee8a937ed4db438360f2f78d0a8cb9a24 Mon Sep 17 00:00:00 2001
-From: =?UTF-8?q?Timo=20Ter=C3=A4s?= <timo.teras@iki.fi>
-Date: Wed, 14 May 2014 10:53:56 +0300
-Subject: [PATCH] implement %y and %C specifiers in strptime
-
----
- src/time/strptime.c | 14 ++++++++++----
- 1 file changed, 10 insertions(+), 4 deletions(-)
-
-diff --git a/src/time/strptime.c b/src/time/strptime.c
-index 4d9eea4..f41f55f 100644
---- a/src/time/strptime.c
-+++ b/src/time/strptime.c
-@@ -11,6 +11,7 @@ char *strptime(const char *restrict s, const char *restrict f, struct tm *restri
- int i, w, neg, adj, min, range, *dest, dummy;
- const char *ex;
- size_t len;
-+ int want_century = 0, century = 0;
- while (*f) {
- if (*f != '%') {
- if (isspace(*f)) for (; *s && isspace(*s); s++);
-@@ -40,9 +41,9 @@ char *strptime(const char *restrict s, const char *restrict f, struct tm *restri
- if (!s) return 0;
- break;
- case 'C':
-- /* FIXME */
-- dest = &dummy;
-+ dest = &century;
- if (w<0) w=2;
-+ want_century |= 2;
- goto numeric_digits;
- case 'd': case 'e':
- dest = &tm->tm_mday;
-@@ -135,14 +136,15 @@ char *strptime(const char *restrict s, const char *restrict f, struct tm *restri
- if (!s) return 0;
- break;
- case 'y':
-- /* FIXME */
-- dest = &dummy;
-+ dest = &tm->tm_year;
- w = 2;
-+ want_century |= 1;
- goto numeric_digits;
- case 'Y':
- dest = &tm->tm_year;
- if (w<0) w=4;
- adj = 1900;
-+ want_century = 0;
- goto numeric_digits;
- case '%':
- if (*s++ != '%') return 0;
-@@ -187,5 +189,9 @@ char *strptime(const char *restrict s, const char *restrict f, struct tm *restri
- ;
- }
- }
-+ if (want_century) {
-+ if (want_century & 2) tm->tm_year += century * 100 - 1900;
-+ else if (tm->tm_year <= 68) tm->tm_year += 100;
-+ }
- return (char *)s;
- }
---
-1.9.3
-
diff --git a/main/musl/APKBUILD b/main/musl/APKBUILD
index 450d0d3d8..80968cabb 100644
--- a/main/musl/APKBUILD
+++ b/main/musl/APKBUILD
@@ -1,8 +1,8 @@
# Contributor: William Pitcock <nenolod@dereferenced.org>
# Maintainer: Timo Teräs <timo.teras@iki.fi>
pkgname=musl
-pkgver=1.1.1
-pkgrel=3
+pkgver=1.1.2
+pkgrel=0
pkgdesc="the musl c library (libc) implementation"
url="http://www.musl-libc.org/"
arch="all"
@@ -13,12 +13,8 @@ makedepends="$depends_dev"
install=""
subpackages="$pkgname-dev $pkgname-utils"
source="http://www.musl-libc.org/releases/musl-$pkgver.tar.gz
- 0001-v1.1.1-to-76f440cf.patch
- 0002-76f440cf-to-d85d261e.patch
- 0003-d85d261e-to-2abb70c3.patch
1001-add-basic-dns-record-parsing-functions.patch
1002-reimplement-if_nameindex-and-getifaddrs-using-netlin.patch
- 1003-implement-y-and-C-specifiers-in-strptime.patch
2001-default-to-localtime-timezone-if-TZ-is-undefined.patch
ldconfig
@@ -120,13 +116,9 @@ utils() {
install -D -m755 "$srcdir"/ldconfig "$subpkgdir"/sbin
}
-md5sums="dbc08d311148e095016d9bbf6c7ffda6 musl-1.1.1.tar.gz
-d4a40fe1656115b2956065ab48e0b372 0001-v1.1.1-to-76f440cf.patch
-0b0dce47217fe25eeb82a7f70e15629f 0002-76f440cf-to-d85d261e.patch
-4e7a277d2aa6ca246bca81996f247379 0003-d85d261e-to-2abb70c3.patch
+md5sums="a81309e54efdf9c68baf679790fc5678 musl-1.1.2.tar.gz
a3810683ef61ac27e2f6ec9801280c81 1001-add-basic-dns-record-parsing-functions.patch
83c3bd2a50b1de5ef948704d3f4e0583 1002-reimplement-if_nameindex-and-getifaddrs-using-netlin.patch
-fc3feec4104a4b25781df92dd96b9eec 1003-implement-y-and-C-specifiers-in-strptime.patch
e936297ceb484b2160a4cd8a3a4eb291 2001-default-to-localtime-timezone-if-TZ-is-undefined.patch
013be8897f27c3909ada59c62020502f ldconfig
61c6c1e84ed1df82abbe6d75e90cf21c getopt_long.c
@@ -134,13 +126,9 @@ e936297ceb484b2160a4cd8a3a4eb291 2001-default-to-localtime-timezone-if-TZ-is-un
cb82d21fed17a116b44b830adba71c5a getconf.c
2b941c4251cac44988a4abfc50e21267 getent.c
45f92f8d59cf84d765de698a9578dbf4 iconv.c"
-sha256sums="9dd75d6512e44d5a13254e246db56c90365894b05bab2b1127e44a31e4fd7c36 musl-1.1.1.tar.gz
-40f241a8aa59621d8a9e6a616df27c38e0a622243bf7346cc98ec1c37454e92a 0001-v1.1.1-to-76f440cf.patch
-d0f4dbc8f0e72df02fcb12e75f829d50909c6da222a5f6a13a0e0c991f91d56e 0002-76f440cf-to-d85d261e.patch
-b931c40613923925ac28a010e4ffbe13380a056dfd01eeccc3a090f598edeaff 0003-d85d261e-to-2abb70c3.patch
+sha256sums="dac94112b9a22d2657cd3f36ca0d62ee1eb10707a22bfc97d5746147ef92852b musl-1.1.2.tar.gz
758390768b1bc4159d56908ca332b9640cd0552ed3b4b2b8d4a6d499c54c11a1 1001-add-basic-dns-record-parsing-functions.patch
1c25880095e869b827f02997e864fdf4bf157a4e923e52d97dbd05e657aedb70 1002-reimplement-if_nameindex-and-getifaddrs-using-netlin.patch
-c22338bc33e8c0c22b280c392b37a0903e13562e671f5ebade09ed5b1d33e2ae 1003-implement-y-and-C-specifiers-in-strptime.patch
60d7aa78040ee664681e507475129f76e445291863137e568c9a3d11ae8436ce 2001-default-to-localtime-timezone-if-TZ-is-undefined.patch
398dc26ec82cc6af056c738e8ac62da212ba978229d9839eb8b61f7ce536da4a ldconfig
d9b644ec20bc33e81a7c52b9fcf7973d835923a69faf50f03db45534b811bd96 getopt_long.c
@@ -148,13 +136,9 @@ d9b644ec20bc33e81a7c52b9fcf7973d835923a69faf50f03db45534b811bd96 getopt_long.c
1b540709f83b7b9a03073b39066810fdb90537d840b50c2016a84bedce038606 getconf.c
68373a55e89ce85c562d941ccf588337d6cc6c9c17689d695f65cd7607134bbe getent.c
f79a2930a2e5bb0624321589edf8b889d1e9b603e01e6b7ae214616605b3fdd7 iconv.c"
-sha512sums="5182deb80a35c8a4009d71098c95a16e5ab9bd03186443917652f0c521d2980183e203256493a69e8230b6a0c4848ca8e44de9e8c851a511cd37d0d41f91b14f musl-1.1.1.tar.gz
-30906a5f7a01ff05693e5a2e72f6c7e75ff7939c28a32b9e777d14d59412bb9df603a09aa8dd693e9a0b70525474a62f7bc657425032a3a5f4b339667e6f62ec 0001-v1.1.1-to-76f440cf.patch
-358f3828367f5a86806ce5be5842c2be44c1a7919133ab83a7c549bc55be847fee2a938c201782db771ff6a5a994cab6ee7c2050f6ae564f4993c0b3825faa36 0002-76f440cf-to-d85d261e.patch
-5bba3f6e369ae38536634cc181b629158dab515476577617024c585ad2247f17bec79b9de035063bddddad07df204654b7eae829b6deb856867907c762f5d2c7 0003-d85d261e-to-2abb70c3.patch
+sha512sums="54d279efea6e122567c936e47401df5c0f1493c42eb3199b0ba3053b1882a864fc1a71d19ad945bc4f328407231c54a7897413e37f4bc33337a243c044a26b4a musl-1.1.2.tar.gz
dad965258daf69371b844f76bfe5a914b0eca0ca76f3fc340b8fd7acf598b5f87bbe6d68b1f43ed0293ee0ed3bfd85d5173ccc169aa6265646248d5b8a906708 1001-add-basic-dns-record-parsing-functions.patch
72cf33738d2cf31f6ec02312bc494d754c17470b519172bb8bd7e2e29ac3b119023088a2b3fbc0dbc2fddd0078ccbae62096106cae361f8c31d6a9950043af25 1002-reimplement-if_nameindex-and-getifaddrs-using-netlin.patch
-48082d2348de40bc6b455266c5552a62e1e75f926e69116c61c8a3cb35fefdff136dc771bf25ee7d43c959834921221112ed7afcc45fcadbcf07562510786916 1003-implement-y-and-C-specifiers-in-strptime.patch
8d4cae760895a18e83b5fcbdc925705a6dd98acd2270562ee6c905363096a4111cf3aa324b52a16066e30bddc9ab104883e2b25b5c68396ea27f1c50cb939f0a 2001-default-to-localtime-timezone-if-TZ-is-undefined.patch
33e13d2242063f3dc9ec199ae9528e469a52ccae4d3726faa3c866e0c7dcf546f69294f9c00307324cee05fd965f84350ae100b8b1138f9d9c8c916de04ab0d1 ldconfig
140f3f20d30bd95ebce8c41b8cc7f616c6cbedf4ea06c729c21014e74f6043796825cc40ebc5180620ea38173afdba23f09ebf6d8b11fa05440b14d23764fca9 getopt_long.c