diff mbox series

[v1] package/ntpsec: new package

Message ID 20211025212541.12280-1-ps.report@gmx.net
State Superseded
Headers show
Series [v1] package/ntpsec: new package | expand

Commit Message

Peter Seiderer Oct. 25, 2021, 9:25 p.m. UTC
- set 'CC=gcc' to avoid cross-compile failure (see [1]):

  /bin/sh: line 1: .../build/ntpsec-1_2_0/build/host/ntpd/keyword-gen: cannot execute binary file: Exec format error

  Waf: Leaving directory `.../build/ntpsec-1_2_0/build/host'
  Build failed
   -> task in 'ntp_keyword.h' failed with exit status 126 (run with -v to display more information)

- set '-std=gnu99"' to avoid compile failure with old compilers

- explicit set PYTHON_CONFIG

- add patch 001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch to
  fix ntptime jfmt5/ofmt5 jfmt6/ofmt6 related compile failure

- add SYSV init file (S49ntp)

- add example ntpd.conf (with legacy option enabled and provide skeleton
  for NTS configuration)

- add config option for NTS support

- depend on python3 (omit python2 to reduce test effort)

- add ntp user/group and run ntpd as restricted user

- add libcap dependency (compile time optional but needed for droproot
  support)

[1] https://gitlab.com/NTPsec/ntpsec/-/issues/694

Signed-off-by: Peter Seiderer <ps.report@gmx.net>
---
 DEVELOPERS                                    |  1 +
 package/Config.in                             |  1 +
 ...5-ofmt5-jfmt6-ofmt6-related-compile-.patch | 61 ++++++++++++++++
 package/ntpsec/Config.in                      | 31 ++++++++
 package/ntpsec/S49ntp                         | 58 +++++++++++++++
 package/ntpsec/ntpd.etc.conf                  | 33 +++++++++
 package/ntpsec/ntpsec.hash                    |  4 ++
 package/ntpsec/ntpsec.mk                      | 71 +++++++++++++++++++
 8 files changed, 260 insertions(+)
 create mode 100644 package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch
 create mode 100644 package/ntpsec/Config.in
 create mode 100644 package/ntpsec/S49ntp
 create mode 100644 package/ntpsec/ntpd.etc.conf
 create mode 100644 package/ntpsec/ntpsec.hash
 create mode 100644 package/ntpsec/ntpsec.mk

Comments

Peter Seiderer Oct. 28, 2021, 9:01 p.m. UTC | #1
Hello Waldemar, *,

On Mon, 25 Oct 2021 23:25:41 +0200, Peter Seiderer <ps.report@gmx.net> wrote:

> - set 'CC=gcc' to avoid cross-compile failure (see [1]):
> 
>   /bin/sh: line 1: .../build/ntpsec-1_2_0/build/host/ntpd/keyword-gen: cannot execute binary file: Exec format error
> 
>   Waf: Leaving directory `.../build/ntpsec-1_2_0/build/host'
>   Build failed
>    -> task in 'ntp_keyword.h' failed with exit status 126 (run with -v to display more information)  
> 
> - set '-std=gnu99"' to avoid compile failure with old compilers
> 
> - explicit set PYTHON_CONFIG
> 
> - add patch 001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch to
>   fix ntptime jfmt5/ofmt5 jfmt6/ofmt6 related compile failure
> 
> - add SYSV init file (S49ntp)
> 
> - add example ntpd.conf (with legacy option enabled and provide skeleton
>   for NTS configuration)
> 
> - add config option for NTS support
> 
> - depend on python3 (omit python2 to reduce test effort)
> 
> - add ntp user/group and run ntpd as restricted user
> 
> - add libcap dependency (compile time optional but needed for droproot
>   support)
> 
> [1] https://gitlab.com/NTPsec/ntpsec/-/issues/694
> 
> Signed-off-by: Peter Seiderer <ps.report@gmx.net>
> ---
>  DEVELOPERS                                    |  1 +
>  package/Config.in                             |  1 +
>  ...5-ofmt5-jfmt6-ofmt6-related-compile-.patch | 61 ++++++++++++++++
>  package/ntpsec/Config.in                      | 31 ++++++++
>  package/ntpsec/S49ntp                         | 58 +++++++++++++++
>  package/ntpsec/ntpd.etc.conf                  | 33 +++++++++
>  package/ntpsec/ntpsec.hash                    |  4 ++
>  package/ntpsec/ntpsec.mk                      | 71 +++++++++++++++++++
>  8 files changed, 260 insertions(+)
>  create mode 100644 package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch
>  create mode 100644 package/ntpsec/Config.in
>  create mode 100644 package/ntpsec/S49ntp
>  create mode 100644 package/ntpsec/ntpd.etc.conf
>  create mode 100644 package/ntpsec/ntpsec.hash
>  create mode 100644 package/ntpsec/ntpsec.mk
> 
> diff --git a/DEVELOPERS b/DEVELOPERS
> index 771519fd9b..593526e61f 100644
> --- a/DEVELOPERS
> +++ b/DEVELOPERS
> @@ -2167,6 +2167,7 @@ F:	package/iwd/
>  F:	package/libevdev/
>  F:	package/libuev/
>  F:	package/log4cplus/
> +F:	package/ntpsec/
>  F:	package/postgresql/
>  F:	package/python-colorzero/
>  F:	package/python-flask-wtf/
> diff --git a/package/Config.in b/package/Config.in
> index d40eb9dabc..842e555342 100644
> --- a/package/Config.in
> +++ b/package/Config.in
> @@ -2256,6 +2256,7 @@ endif
>  	source "package/nmap/Config.in"
>  	source "package/noip/Config.in"
>  	source "package/ntp/Config.in"
> +	source "package/ntpsec/Config.in"
>  	source "package/nuttcp/Config.in"
>  	source "package/odhcp6c/Config.in"
>  	source "package/odhcploc/Config.in"
> diff --git a/package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch b/package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch
> new file mode 100644
> index 0000000000..c2838fe8e0
> --- /dev/null
> +++ b/package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch
> @@ -0,0 +1,61 @@
> +From 4015a1183d2f79dad6dd675ca5e0d329825f3fa3 Mon Sep 17 00:00:00 2001
> +From: Peter Seiderer <ps.report@gmx.net>
> +Date: Mon, 4 Oct 2021 22:25:58 +0200
> +Subject: [PATCH] ntptime: fix jfmt5/ofmt5 jfmt6/ofmt6 related compile failure
> +MIME-Version: 1.0
> +Content-Type: text/plain; charset=UTF-8
> +Content-Transfer-Encoding: 8bit
> +
> +Use same define guard for definiton as for usage ('HAVE_STRUCT_NTPTIMEVAL_TAI'
> +instead of 'NTP_API && NTP_API > 3').
> +
> +Fixes:
> +
> +  ../../ntptime/ntptime.c: In function ‘main’:
> +  ../../ntptime/ntptime.c:349:17: error: ‘jfmt5’ undeclared (first use in this function); did you mean ‘jfmt6’?
> +    349 |   printf(json ? jfmt5 : ofmt5, (long)ntv.tai);
> +        |                 ^~~~~
> +        |                 jfmt6
> +  ../../ntptime/ntptime.c:349:17: note: each undeclared identifier is reported only once for each function it appears in
> +  ../../ntptime/ntptime.c:349:25: error: ‘ofmt5’ undeclared (first use in this function); did you mean ‘ofmt6’?
> +    349 |   printf(json ? jfmt5 : ofmt5, (long)ntv.tai);
> +        |                         ^~~~~
> +        |                         ofmt6
> +  ../../ntptime/ntptime.c:321:15: warning: unused variable ‘jfmt6’ [-Wunused-variable]
> +    321 |   const char *jfmt6 = "";
> +        |               ^~~~~
> +  ../../ntptime/ntptime.c:311:15: warning: unused variable ‘ofmt6’ [-Wunused-variable]
> +    311 |   const char *ofmt6 = "\n";
> +        |               ^~~~~
> +
> +[Upstream: https://gitlab.com/NTPsec/ntpsec/-/merge_requests/1245]
> +Signed-off-by: Peter Seiderer <ps.report@gmx.net>
> +---
> + ntptime/ntptime.c | 4 ++--
> + 1 file changed, 2 insertions(+), 2 deletions(-)
> +
> +diff --git a/ntptime/ntptime.c b/ntptime/ntptime.c
> +index ff861cb..5d58593 100644
> +--- a/ntptime/ntptime.c
> ++++ b/ntptime/ntptime.c
> +@@ -305,7 +305,7 @@ main(
> + 		const char *ofmt2 = "  time %s, (.%0*d),\n";
> + 		const char *ofmt3 = "  maximum error %lu us, estimated error %lu us";
> + 		const char *ofmt4 = "  ntptime=%x.%x unixtime=%x.%0*d %s";
> +-#if defined NTP_API && NTP_API > 3
> ++#if defined(HAVE_STRUCT_NTPTIMEVAL_TAI)
> + 		const char *ofmt5 = ", TAI offset %ld\n";
> + #else
> + 		const char *ofmt6 = "\n";
> +@@ -315,7 +315,7 @@ main(
> + 		const char *jfmt2 = "\"time\":\"%s\",\"fractional-time\":\".%0*d\",";
> + 		const char *jfmt3 = "\"maximum-error\":%lu,\"estimated-error\":%lu,";
> + 		const char *jfmt4 = "\"raw-ntp-time\":\"%x.%x\",\"raw-unix-time\":\"%x.%0*d %s\",";
> +-#if defined NTP_API && NTP_API > 3
> ++#if defined(HAVE_STRUCT_NTPTIMEVAL_TAI)
> + 		const char *jfmt5 = "\"TAI-offset\":%d,";
> + #else
> + 		const char *jfmt6 = "";
> +-- 
> +2.33.0
> +
> diff --git a/package/ntpsec/Config.in b/package/ntpsec/Config.in
> new file mode 100644
> index 0000000000..7275533d26
> --- /dev/null
> +++ b/package/ntpsec/Config.in
> @@ -0,0 +1,31 @@
> +config BR2_PACKAGE_NTPSEC
> +	bool "ntpsec"
> +	depends on BR2_PACKAGE_PYTHON3
> +	select BR2_PACKAGE_LIBCAP
> +	select BR2_PACKAGE_OPENSSL
> +	help
> +	  NTPsec project - a secure, hardened, and improved
> +	  implementation of Network Time Protocol derived
> +	  from NTP Classic, Dave Mills’s original.
> +
> +	  Provides things like ntpd, ntpdate, ntpq, etc...
> +
> +	  https://www.ntpsec.org/
> +
> +if BR2_PACKAGE_NTPSEC
> +
> +config BR2_PACKAGE_NTPSEC_CLASSIC_MODE
> +	bool "classic-mode"
> +	help
> +	  Enable strict configuration and log-format compatibility
> +	  with NTP Classic.
> +
> +config BR2_PACKAGE_NTPSEC_NTS
> +	bool "NTS support"
> +	help
> +	  Enable Network Time Security (NTS) support.
> +
> +endif
> +
> +comment "ntpsec depens on Pyhton3"
> +	depends on !BR2_PACKAGE_PYTHON3
> diff --git a/package/ntpsec/S49ntp b/package/ntpsec/S49ntp
> new file mode 100644
> index 0000000000..f3db51418e
> --- /dev/null
> +++ b/package/ntpsec/S49ntp
> @@ -0,0 +1,58 @@
> +#!/bin/sh
> +#
> +# Starts Network Time Protocol daemon
> +#
> +
> +DAEMON="ntpd"
> +PIDFILE="/var/run/$DAEMON.pid"
> +
> +NTPD_ARGS="-g -u ntp:ntp -s /var/run/ntp"
> +
> +# shellcheck source=/dev/null
> +[ -r "/etc/default/$DAEMON" ] && . "/etc/default/$DAEMON"
> +
> +mkdir -p /var/run/ntp && chown ntp:ntp /var/run/ntp
> +
> +start() {
> +	printf 'Starting %s: ' "$DAEMON"
> +	# shellcheck disable=SC2086 # we need the word splitting
> +	start-stop-daemon -S -q -p "$PIDFILE" -x "/usr/sbin/$DAEMON" \
> +		-- $NTPD_ARGS -p "$PIDFILE"
> +	status=$?
> +	if [ "$status" -eq 0 ]; then
> +		echo "OK"
> +	else
> +		echo "FAIL"
> +	fi
> +	return "$status"
> +}
> +
> +stop() {
> +	printf 'Stopping %s: ' "$DAEMON"
> +	start-stop-daemon -K -q -p "$PIDFILE"
> +	status=$?
> +	if [ "$status" -eq 0 ]; then
> +		rm -f "$PIDFILE"
> +		echo "OK"
> +	else
> +		echo "FAIL"
> +	fi
> +	return "$status"
> +}
> +
> +restart() {
> +	stop
> +	sleep 1
> +	start
> +}
> +
> +case "$1" in
> +	start|stop|restart)
> +		"$1";;
> +	reload)
> +		# Restart, since there is no true "reload" feature.
> +		restart;;
> +	*)
> +		echo "Usage: $0 {start|stop|restart|reload}"
> +		exit 1
> +esac
> diff --git a/package/ntpsec/ntpd.etc.conf b/package/ntpsec/ntpd.etc.conf
> new file mode 100644
> index 0000000000..e0f45c1438
> --- /dev/null
> +++ b/package/ntpsec/ntpd.etc.conf
> @@ -0,0 +1,33 @@
> +#
> +# legacy NTP configuration
> +#
> +pool 0.pool.ntp.org iburst
> +pool 1.pool.ntp.org iburst
> +pool 2.pool.ntp.org iburst
> +pool 3.pool.ntp.org iburst
> +
> +#
> +# NTS configuration
> +#
> +# Notes:
> +#  - uncomment the following lines to enable NTS support (but
> +#    make sure the initial clock is up-to-date (otherwise the
> +#    NTS certificate validation will fail with 'NTSc: certificate invalid:
> +#    9=>certificate is not yet valid' as on boards without RTC support)
> +#    and/or keep at least one line from the legacy NTP lines
> +#  - enable BR2_PACKAGE_CA_CERTIFICATES to gain access to the certificate
> +#    files
> +#
> +# server time.cloudflare.com nts  # Global, anycast
> +# server nts.ntp.se:4443 nts      # Sweden
> +# server ntpmon.dcs1.biz nts      # Singapore
> +# server ntp1.glypnod.com nts     # San Francisco
> +# server ntp2.glypnod.com nts     # London
> +#
> +# ca /usr/share/ca-certificates/mozilla
> +
> +# Allow only time queries, at a limited rate, sending KoD when in excess.
> +# Allow all local queries (IPv4, IPv6)
> +restrict default nomodify nopeer noquery limited kod
> +restrict 127.0.0.1
> +restrict [::1]
> diff --git a/package/ntpsec/ntpsec.hash b/package/ntpsec/ntpsec.hash
> new file mode 100644
> index 0000000000..9c30605cbd
> --- /dev/null
> +++ b/package/ntpsec/ntpsec.hash
> @@ -0,0 +1,4 @@
> +# Locally calculated
> +sha256  80e5b4c07dc1f8f7dc90851662c72a80a4111477c48040ae9e1f2e56f893251d  ntpsec-NTPsec_1_2_0.tar.bz2
> +sha256  b4db4de3317c3b0554ed91eb692968800bdfd6ad2c16ffbeee8ce4895ed91da4  LICENSE.adoc
> +sha256  d3b21470adadd9abd9c6d675378f8c371ac5a4ea6dbec91859e02fadca3c0856  docs/copyright.adoc
> diff --git a/package/ntpsec/ntpsec.mk b/package/ntpsec/ntpsec.mk
> new file mode 100644
> index 0000000000..c62077dce6
> --- /dev/null
> +++ b/package/ntpsec/ntpsec.mk
> @@ -0,0 +1,71 @@
> +################################################################################
> +#
> +# ntpsec
> +#
> +################################################################################
> +
> +NTPSEC_VERSION_MAJOR = 1
> +NTPSEC_VERSION_MINOR = 2
> +NTPSEC_VERSION_POINT = 0
> +NTPSEC_VERSION = $(NTPSEC_VERSION_MAJOR)_$(NTPSEC_VERSION_MINOR)_$(NTPSEC_VERSION_POINT)
> +NTPSEC_SOURCE = ntpsec-NTPsec_$(NTPSEC_VERSION).tar.bz2
> +NTPSEC_SITE = https://gitlab.com/NTPsec/ntpsec/-/archive/NTPsec_$(NTPSEC_VERSION)
> +NTPSEC_LICENSE = BSD-2-Clause NTP BSD-3-Clause MIT
> +NTPSEC_LICENSE_FILES = LICENSE.adoc docs/copyright.adoc
> +
> +NTPSEC_CPE_ID_VENDOR = ntpsec
> +NTPSEC_CPE_ID_VERSION = $(NTPSEC_VERSION_MAJOR).$(NTPSEC_VERSION_MINOR)
> +NTPSEC_CPE_ID_UPDATE = $(NTPSEC_VERSION_POINT)
> +
> +NTPSEC_DEPENDENCIES = \
> +	host-pkgconf \
> +	$(if $(BR2_PACKAGE_PYTHON),python,python3) \
> +	libcap \
> +	openssl
> +
> +NTPSEC_CONF_OPTS = \
> +	CC=gcc \
> +	PYTHON_CONFIG="$(STAGING_DIR)/usr/bin/$(if $(BR2_PACKAGE_PYTHON),python,python3)-config" \
> +	--cross-compiler="$(TARGET_CC)" \
> +	--cross-cflags="$(TARGET_CFLAGS) -std=gnu99" \
> +	--cross-ldflags="$(TARGET_LDFLAGS)" \
> +	--notests \
> +	--enable-early-droproot \
> +	--disable-mdns-registration \
> +	--enable-pylib=ffi \
> +	--nopyc \
> +	--nopyo \
> +	--nopycache \
> +	--disable-doc \
> +	--disable-manpage
> +
> +ifeq ($(BR2_PACKAGE_NTPSEC_CLASSIC_MODE),y)
> +NTPSEC_CONF_OPTS += --enable-classic-mode
> +endif
> +
> +ifeq ($(BR2_PACKAGE_NTPSEC_NTS),y)
> +#NTPSEC_CONF_OPTS += --enable-nts
> +else
> +NTPSEC_CONF_OPTS += --disable-nts
> +endif
> +
> +# add a link to libntpc.so where python searches for it
> +define NTPSEC_LIBNTPC_LINK
> +	ln -sf /usr/lib/ntp/libntpc.so $(TARGET_DIR)/usr/lib/libntpc.so
> +endef
> +NTPSEC_POST_INSTALL_TARGET_HOOKS += NTPSEC_LIBNTPC_LINK
> +
> +define NTPSEC_INSTALL_NTPSEC_CONF
> +	$(INSTALL) -m 644 package/ntpsec/ntpd.etc.conf $(TARGET_DIR)/etc/ntp.conf
> +endef
> +NTPSEC_POST_INSTALL_TARGET_HOOKS += NTPSEC_INSTALL_NTPSEC_CONF
> +
> +define NTPSEC_INSTALL_INIT_SYSV
> +	$(INSTALL) -D -m 755 package/ntpsec/S49ntp $(TARGET_DIR)/etc/init.d/S49ntp
> +endef
> +
> +define NTPSEC_USERS
> +	ntp -1 ntp -1 * - - - ntpd user
> +endef
> +
> +$(eval $(waf-package))


The resulting ntpd runs fine with the raspberrypi3_defconfig, but segfaults
when compiled/used with raspberrypi3_64_defconfig (uclibc, -Os):

	$ /usr/sbin/ntpd -n -d -g
1970-01-01T00:04:18 ntpd[263]: INIT: ntpd ntpsec-1.2.0 2021-10-24T13:39:21Z: Starting
1970-01-01T00:04:18 ntpd[263]: INIT: Command line: /usr/sbin/ntpd -n -d
1970-01-01T00:04:18 ntpd[263]: INIT: precision = 7.291 usec (-17)
1970-01-01T00:04:18 ntpd[263]: INIT: successfully locked into RAM
1970-01-01T00:04:18 ntpd[263]: CONFIG: readconfig: parsing file: /etc/ntp.conf
1970-01-01T00:04:18 ntpd[263]: CONFIG: restrict nopeer ignored
1970-01-01T00:04:18 ntpd[263]: INIT: Using SO_TIMESTAMPNS
1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 0 v6wildcard [::]:123
1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 1 v4wildcard 0.0.0.0:123
1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 2 lo 127.0.0.1:123
1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 3 eth0 172.16.0.30:123
1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 4 lo [::1]:123
1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 5 eth0 [fe80::ba27:ebff:fea6:340%2]:123
1970-01-01T00:04:18 ntpd[263]: IO: Listening on routing socket on fd #22 for interface updates
1970-01-01T00:04:19 ntpd[263]: SYNC: Found 10 servers, suggest minsane at least 3
1970-01-01T00:04:19 ntpd[263]: INIT: MRU 10922 entries, 13 hash bits, 65536 bytes
1970-01-01T00:04:20 ntpd[263]: DNS: dns_probe: 0.pool.ntp.org, cast_flags:8, flags:101
Segmentation fault (core dumped)


With the following stacktrace:

	$ ./host/bin/aarch64-buildroot-linux-uclibc-gdb build/ntpsec-1_2_0/build/main/ntpd/ntpd core
Program terminated with signal SIGSEGV, Segmentation fault.
(gdb) where
#0  0x0000007fbbfa4150 in res_sync_func () at libc/inet/resolv.c:3356
#1  0x0000007fbbfa1468 in __open_nameservers () at libc/inet/resolv.c:949
#2  0x0000007fbbfa0498 in __dns_lookup (name=0x55a464a7f0 "0.pool.ntp.org",
    type=1, outpacket=0x7fbbf16c48, a=0x7fbbf16c08) at libc/inet/resolv.c:1134
#3  0x0000007fbbfa2744 in __GI_gethostbyname_r (
    name=0x55a464a7f0 "0.pool.ntp.org", result_buf=0x7fbbf17628,
    buf=0x7fbbf16d90 "", buflen=992, result=0x7fbbf17670,
    h_errnop=0x7fbbf17668) at libc/inet/resolv.c:1966
#4  0x0000007fbbfa29a0 in __GI_gethostbyname2_r (
    name=0x55a464a7f0 "0.pool.ntp.org", family=2, result_buf=0x7fbbf17628,
    buf=0x7fbbf16d70 "0.pool.ntp.org", buflen=1024, result=0x7fbbf17670,
    h_errnop=0x7fbbf17668) at libc/inet/resolv.c:2065
#5  0x0000007fbbf9b924 in gaih_inet (name=0x55a464a7f0 "0.pool.ntp.org",
    service=0x7fbbf17828, req=0x7fbbf17890, pai=0x7fbbf17838)
    at libc/inet/getaddrinfo.c:596
#6  0x0000007fbbf9c624 in __GI_getaddrinfo (
    name=0x55a464a7f0 "0.pool.ntp.org",
    service=0x5576ad807d "\277\261\377\377A\215E\001I9\334r\263f\017\037D",
    hints=0x7fbbf17890, pai=0x5576b00bd8) at libc/inet/getaddrinfo.c:957
#7  0x0000005576ac5698 in _start ()

(gdb) p _res
$1 = {options = 0, nsaddr_list = {{sin_family = 0, sin_port = 0, sin_addr = {
        s_addr = 0}, sin_zero = "\000\000\000\000\000\000\000"}, {
      sin_family = 0, sin_port = 0, sin_addr = {s_addr = 0},
      sin_zero = "\000\000\000\000\000\000\000"}, {sin_family = 0,
      sin_port = 0, sin_addr = {s_addr = 0},
      sin_zero = "\000\000\000\000\000\000\000"}}, dnsrch = {0x0, 0x0, 0x0,
    0x0, 0x0, 0x0, 0x0}, nscount = 0 '\000', ndots = 0 '\000',
  retrans = 0 '\000', retry = 0 '\000', defdname = '\000' <repeats 255 times>,
  nsort = 0 '\000', pfcode = 0, id = 0, res_h_errno = 0, sort_list = {{addr = {
        s_addr = 0}, mask = 0}, {addr = {s_addr = 0}, mask = 0}, {addr = {
        s_addr = 0}, mask = 0}, {addr = {s_addr = 0}, mask = 0}, {addr = {
        s_addr = 0}, mask = 0}, {addr = {s_addr = 0}, mask = 0}, {addr = {
        s_addr = 0}, mask = 0}, {addr = {s_addr = 0}, mask = 0}, {addr = {
        s_addr = 0}, mask = 0}, {addr = {s_addr = 0}, mask = 0}}, _u = {
    _ext = {nsaddrs = {0x0, 0x0, 0x0}, nscount = 0 '\000', nstimes = {0, 0,
        0}, nssocks = {0, 0, 0}, nscount6 = 0, nsinit = 0}}}

(gdb) p &_res
$2 = (struct __res_state *) 0x7fbc014d98 <_res>

(gdb) p rp
$3 = (struct __res_state *) 0x7fffffffff


And the following uclibc code at libc/inet/resolv.c:3356:

3345 static void res_sync_func(void)
3346 {
3347         struct __res_state *rp = &(_res);
3348         int n;
3349 
3350         /* If we didn't get malloc failure earlier... */
3351         if (__nameserver != (void*) &__local_nameserver) {
3352                 /* TODO:
3353                  * if (__nameservers < rp->nscount) - try to grow __nameserver[]?
3354                  */
3355 #ifdef __UCLIBC_HAS_IPV6__
3356                 if (__nameservers > rp->_u._ext.nscount)
3357                         __nameservers = rp->_u._ext.nscount;
3358                 n = __nameservers;


The special thing about ntpsec is the DNS lookup in an extra thread
and/or the call to res_init(), see ntpsec-1_2_0/ntpd/ntp_dns.c:

 69         msyslog(LOG_INFO, "DNS: dns_probe: %s, cast_flags:%x, flags:%x%s",
 70                 hostname, pp->cast_flags, pp->cfg.flags, busy);
 71         if (NULL != active)     /* normally redundant */
 72                 return false;
 73 
 74         active = pp;
 75 
 76         sigfillset(&block_mask);
 77         pthread_sigmask(SIG_BLOCK, &block_mask, &saved_sig_mask);
 78         rc = pthread_create(&worker, NULL, dns_lookup, pp);


and


165 static void* dns_lookup(void* arg)
166 {
167         struct peer *pp = (struct peer *) arg;
168         struct addrinfo hints;
169 
170 #ifdef HAVE_SECCOMP_H
171         setup_SIGSYS_trap();      /* enable trap for this thread */
172 #endif
173 
174 #ifdef HAVE_RES_INIT
175         /* Reload DNS servers from /etc/resolv.conf in case DHCP has updated it.
176          * We only need to do this occasionally, but it's not expensive
177          * and simpler to do it every time than it is to figure out when
178          * to do it.
179          * This res_init() covers NTS too.
180          */
181         res_init();
182 #endif
183 
184         if (pp->cfg.flags & FLAG_NTS) {
185 #ifndef DISABLE_NTS
186                 nts_probe(pp);
187 #endif
188         } else {
189                 ZERO(hints);
190                 hints.ai_protocol = IPPROTO_UDP;
191                 hints.ai_socktype = SOCK_DGRAM;
192                 hints.ai_family = AF(&pp->srcadr);
193                 gai_rc = getaddrinfo(pp->hostname, NTP_PORTA, &hints, &answer);
194         }


The failure can be fixed/work-around with the following uClibc-ng-1.0.39 patch:

diff --git a/libc/inet/resolv.c b/libc/inet/resolv.c
index 8bbd7c7..cf170fb 100644
--- a/libc/inet/resolv.c
+++ b/libc/inet/resolv.c
@@ -3344,7 +3344,7 @@ libc_hidden_def(dn_skipname)
 /* Will be called under __resolv_lock. */
 static void res_sync_func(void)
 {
-	struct __res_state *rp = &(_res);
+	struct __res_state *rp = __res_state();
 	int n;
 
 	/* If we didn't get malloc failure earlier... */
@@ -3896,7 +3896,7 @@ res_ninit(res_state statp)
 #endif /* L_res_init */
 
 #ifdef L_res_state
-# if defined __UCLIBC_HAS_TLS__
+# if !defined __UCLIBC_HAS_TLS__
 struct __res_state *
 __res_state (void)
 {


The first change is using the provided __res_state() method instead
of direct access, the second one changes the __res_state() implementation
to the one where the comment 'When threaded, _res may be a per-thread variable.'
indicates this should be used with threads/TLS enabled...

Not sure if this is the right fix and/or I figrue out enough of the uclibc
logic about the _res access vs. res_init() vs. thread/TLS logic...

Regards,
Peter
Waldemar Brodkorb Oct. 30, 2021, 10:56 p.m. UTC | #2
Hi Peter,
Peter Seiderer wrote,

> Hello Waldemar, *,
> 
> On Mon, 25 Oct 2021 23:25:41 +0200, Peter Seiderer <ps.report@gmx.net> wrote:
> 
> The resulting ntpd runs fine with the raspberrypi3_defconfig, but segfaults
> when compiled/used with raspberrypi3_64_defconfig (uclibc, -Os):
> 
> 	$ /usr/sbin/ntpd -n -d -g
> 1970-01-01T00:04:18 ntpd[263]: INIT: ntpd ntpsec-1.2.0 2021-10-24T13:39:21Z: Starting
> 1970-01-01T00:04:18 ntpd[263]: INIT: Command line: /usr/sbin/ntpd -n -d
> 1970-01-01T00:04:18 ntpd[263]: INIT: precision = 7.291 usec (-17)
> 1970-01-01T00:04:18 ntpd[263]: INIT: successfully locked into RAM
> 1970-01-01T00:04:18 ntpd[263]: CONFIG: readconfig: parsing file: /etc/ntp.conf
> 1970-01-01T00:04:18 ntpd[263]: CONFIG: restrict nopeer ignored
> 1970-01-01T00:04:18 ntpd[263]: INIT: Using SO_TIMESTAMPNS
> 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 0 v6wildcard [::]:123
> 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 1 v4wildcard 0.0.0.0:123
> 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 2 lo 127.0.0.1:123
> 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 3 eth0 172.16.0.30:123
> 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 4 lo [::1]:123
> 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 5 eth0 [fe80::ba27:ebff:fea6:340%2]:123
> 1970-01-01T00:04:18 ntpd[263]: IO: Listening on routing socket on fd #22 for interface updates
> 1970-01-01T00:04:19 ntpd[263]: SYNC: Found 10 servers, suggest minsane at least 3
> 1970-01-01T00:04:19 ntpd[263]: INIT: MRU 10922 entries, 13 hash bits, 65536 bytes
> 1970-01-01T00:04:20 ntpd[263]: DNS: dns_probe: 0.pool.ntp.org, cast_flags:8, flags:101
> Segmentation fault (core dumped)

Could you add a small C test program to uClibc-ng-test to trigger
the bug? That would help to find any regression to targets without
TLS support.

best regards
 Waldemar
Peter Seiderer Nov. 4, 2021, 8:30 p.m. UTC | #3
Hello Waldemar,

On Sun, 31 Oct 2021 00:56:56 +0200, Waldemar Brodkorb <wbx@openadk.org> wrote:

> Hi Peter,
> Peter Seiderer wrote,
>
> > Hello Waldemar, *,
> >
> > On Mon, 25 Oct 2021 23:25:41 +0200, Peter Seiderer <ps.report@gmx.net> wrote:
> >
> > The resulting ntpd runs fine with the raspberrypi3_defconfig, but segfaults
> > when compiled/used with raspberrypi3_64_defconfig (uclibc, -Os):
> >
> > 	$ /usr/sbin/ntpd -n -d -g
> > 1970-01-01T00:04:18 ntpd[263]: INIT: ntpd ntpsec-1.2.0 2021-10-24T13:39:21Z: Starting
> > 1970-01-01T00:04:18 ntpd[263]: INIT: Command line: /usr/sbin/ntpd -n -d
> > 1970-01-01T00:04:18 ntpd[263]: INIT: precision = 7.291 usec (-17)
> > 1970-01-01T00:04:18 ntpd[263]: INIT: successfully locked into RAM
> > 1970-01-01T00:04:18 ntpd[263]: CONFIG: readconfig: parsing file: /etc/ntp.conf
> > 1970-01-01T00:04:18 ntpd[263]: CONFIG: restrict nopeer ignored
> > 1970-01-01T00:04:18 ntpd[263]: INIT: Using SO_TIMESTAMPNS
> > 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 0 v6wildcard [::]:123
> > 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 1 v4wildcard 0.0.0.0:123
> > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 2 lo 127.0.0.1:123
> > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 3 eth0 172.16.0.30:123
> > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 4 lo [::1]:123
> > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 5 eth0 [fe80::ba27:ebff:fea6:340%2]:123
> > 1970-01-01T00:04:18 ntpd[263]: IO: Listening on routing socket on fd #22 for interface updates
> > 1970-01-01T00:04:19 ntpd[263]: SYNC: Found 10 servers, suggest minsane at least 3
> > 1970-01-01T00:04:19 ntpd[263]: INIT: MRU 10922 entries, 13 hash bits, 65536 bytes
> > 1970-01-01T00:04:20 ntpd[263]: DNS: dns_probe: 0.pool.ntp.org, cast_flags:8, flags:101
> > Segmentation fault (core dumped)
>
> Could you add a small C test program to uClibc-ng-test to trigger
> the bug? That would help to find any regression to targets without
> TLS support.

Did take a first look at the uClibc-ng-test regarding the problem,
there is already one test/inet/tst-res test...


For the raspberrypi3_defconfig case (uclibc unpatched):

	$ sh uclibcng-testrunner.sh
[...]
FAIL tst-ethers-line got 1 expected 0
	Cannot open file /etc/ethers: No such file or directory
FAIL tst-ethers got 1 expected 0
	Either /etc/ethers is missing or it has incorrect contents
[...]
FAIL tst-cancel18 got 1 expected 0
	going to cancel in-time
	Timed out: killed the child process
[...]
FAIL tst-cancelx18 got 1 expected 0
	going to cancel in-time
	Timed out: killed the child process
[...]
Total skipped: 15
Total failed: 4
Total passed: 460



For the raspberrypi3_64_defconfig case (uclibc unpatched):

	$ sh uclibcng-testrunner.sh
[...]
FAIL tst-ethers-line got 1 expected 0
	Cannot open file /etc/ethers: No such file or directory
FAIL tst-ethers got 1 expected 0
	Either /etc/ethers is missing or it has incorrect contents
[...]
FAIL tst-res got 139 expected 0
	Segmentation fault (core dumped)
[...]
FAIL tst-seekdir got 1 expected 0
	.
	..
	tst-seekdir.out
	tst-utmpx
	tst-inotify
	tst-mkostemps.out
	seek.out
	tst-scandir
	tst-seekdir
	tst-statvfs.out
	sem
	stdarg.out
	fdopen.out
	tst-utmp
	tst-preadvwritev.out
	bug-glob2.out
	popen
	dirent64.out
	tst-scandir.out
	tst-hasmntopt.out
	tst-statvfs
	bug-glob2
	popen.out
	Makefile
	opendir-tst1
	sem.out
	tst-inotify.out
	tst-syscall0
	tst-statfs.out
	bug-readdir1
	dirent.out
	tst-statfs
	tst-syscall1.out
	tst-syscall0.out
	stdarg
	tst-preadvwritev
	tst-syscall6.out
	tst-mkostemps
	Makefile.in
	tst-utmp.out
	tst-nftw
	opendir-tst1.out
	tst-syscall1
	bug-readdir1.out
	tst-hasmntopt
	tst-syscall6
	fdopen
	seek
	tst-nftw.out
	dirent64
	tst-fnmatch.input
	tst-utmpx.out
	dirent
	going back past 4-th entry...
	seekdir (d, -1600443765); telldir (d) == -1
[...]
FAIL tst-cancel18 got 1 expected 0
	going to cancel in-time
	Timed out: killed the child process
[...]
FAIL tst-cancelx18 got 1 expected 0
	going to cancel in-time
	Timed out: killed the child process
[...]
FAIL tst-tls3 got 1 expected 0

	/usr/lib/uclibc-ng-test/test/tls/tst-tls3: symbol 'baz': can't handle reloc type 0x404
FAIL tst-tls4 got 1 expected 0

	/usr/lib/uclibc-ng-test/test/tls/tst-tls4: symbol 'foo': can't handle reloc type 0x404
FAIL tst-tls5 got 1 expected 0

	/usr/lib/uclibc-ng-test/test/tls/tst-tls5: symbol 'foo': can't handle reloc type 0x404
FAIL tst-tls6 got 1 expected 0

	/usr/lib/uclibc-ng-test/test/tls/tst-tls6: symbol 'foo': can't handle reloc type 0x404
FAIL tst-tls7 got 1 expected 0

	/usr/lib/uclibc-ng-test/test/tls/tst-tls7: symbol 'foo': can't handle reloc type 0x404
FAIL tst-tls8 got 1 expected 0

	/usr/lib/uclibc-ng-test/test/tls/tst-tls8: symbol 'foo': can't handle reloc type 0x404
[...]
Total skipped: 15
Total failed: 12
Total passed: 454


The tst-res Segmentation fault failure can be fixed by
this additional uclibc patch:

--- a/include/resolv.h
+++ b/include/resolv.h
@@ -457,7 +457,7 @@ __END_DECLS
 #    ifndef NOT_IN_libc
 #     define __resp __libc_resp
 #    endif
-#    define _res (*__resp)
+#    define _res (*__res_state())
 extern __thread struct __res_state *__resp attribute_tls_model_ie;
 #   endif
 #  else


Will take a look at some glibc resolv tests and try to port
them (and, if I find enough time, at some of the other
failures)...

Regards,
Peter

>
> best regards
>  Waldemar
Waldemar Brodkorb Nov. 11, 2021, 8:58 a.m. UTC | #4
Hi Peter,
Peter Seiderer wrote,

> Hello Waldemar,
> 
> On Sun, 31 Oct 2021 00:56:56 +0200, Waldemar Brodkorb <wbx@openadk.org> wrote:
> 
> > Hi Peter,
> > Peter Seiderer wrote,
> >
> > > Hello Waldemar, *,
> > >
> > > On Mon, 25 Oct 2021 23:25:41 +0200, Peter Seiderer <ps.report@gmx.net> wrote:
> > >
> > > The resulting ntpd runs fine with the raspberrypi3_defconfig, but segfaults
> > > when compiled/used with raspberrypi3_64_defconfig (uclibc, -Os):
> > >
> > > 	$ /usr/sbin/ntpd -n -d -g
> > > 1970-01-01T00:04:18 ntpd[263]: INIT: ntpd ntpsec-1.2.0 2021-10-24T13:39:21Z: Starting
> > > 1970-01-01T00:04:18 ntpd[263]: INIT: Command line: /usr/sbin/ntpd -n -d
> > > 1970-01-01T00:04:18 ntpd[263]: INIT: precision = 7.291 usec (-17)
> > > 1970-01-01T00:04:18 ntpd[263]: INIT: successfully locked into RAM
> > > 1970-01-01T00:04:18 ntpd[263]: CONFIG: readconfig: parsing file: /etc/ntp.conf
> > > 1970-01-01T00:04:18 ntpd[263]: CONFIG: restrict nopeer ignored
> > > 1970-01-01T00:04:18 ntpd[263]: INIT: Using SO_TIMESTAMPNS
> > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 0 v6wildcard [::]:123
> > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 1 v4wildcard 0.0.0.0:123
> > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 2 lo 127.0.0.1:123
> > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 3 eth0 172.16.0.30:123
> > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 4 lo [::1]:123
> > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 5 eth0 [fe80::ba27:ebff:fea6:340%2]:123
> > > 1970-01-01T00:04:18 ntpd[263]: IO: Listening on routing socket on fd #22 for interface updates
> > > 1970-01-01T00:04:19 ntpd[263]: SYNC: Found 10 servers, suggest minsane at least 3
> > > 1970-01-01T00:04:19 ntpd[263]: INIT: MRU 10922 entries, 13 hash bits, 65536 bytes
> > > 1970-01-01T00:04:20 ntpd[263]: DNS: dns_probe: 0.pool.ntp.org, cast_flags:8, flags:101
> > > Segmentation fault (core dumped)
> >
> > Could you add a small C test program to uClibc-ng-test to trigger
> > the bug? That would help to find any regression to targets without
> > TLS support.
> 
> Did take a first look at the uClibc-ng-test regarding the problem,
> there is already one test/inet/tst-res test...
> 
> 
> For the raspberrypi3_defconfig case (uclibc unpatched):
> 
> 	$ sh uclibcng-testrunner.sh
> [...]
> FAIL tst-ethers-line got 1 expected 0
> 	Cannot open file /etc/ethers: No such file or directory
> FAIL tst-ethers got 1 expected 0
> 	Either /etc/ethers is missing or it has incorrect contents
> [...]
> FAIL tst-cancel18 got 1 expected 0
> 	going to cancel in-time
> 	Timed out: killed the child process
> [...]
> FAIL tst-cancelx18 got 1 expected 0
> 	going to cancel in-time
> 	Timed out: killed the child process
> [...]
> Total skipped: 15
> Total failed: 4
> Total passed: 460
> 
> 
> 
> For the raspberrypi3_64_defconfig case (uclibc unpatched):
> 
> 	$ sh uclibcng-testrunner.sh
> [...]
> FAIL tst-ethers-line got 1 expected 0
> 	Cannot open file /etc/ethers: No such file or directory
> FAIL tst-ethers got 1 expected 0
> 	Either /etc/ethers is missing or it has incorrect contents
> [...]
> FAIL tst-res got 139 expected 0
> 	Segmentation fault (core dumped)
> [...]
> FAIL tst-seekdir got 1 expected 0
> 	.
> 	..
> 	tst-seekdir.out
> 	tst-utmpx
> 	tst-inotify
> 	tst-mkostemps.out
> 	seek.out
> 	tst-scandir
> 	tst-seekdir
> 	tst-statvfs.out
> 	sem
> 	stdarg.out
> 	fdopen.out
> 	tst-utmp
> 	tst-preadvwritev.out
> 	bug-glob2.out
> 	popen
> 	dirent64.out
> 	tst-scandir.out
> 	tst-hasmntopt.out
> 	tst-statvfs
> 	bug-glob2
> 	popen.out
> 	Makefile
> 	opendir-tst1
> 	sem.out
> 	tst-inotify.out
> 	tst-syscall0
> 	tst-statfs.out
> 	bug-readdir1
> 	dirent.out
> 	tst-statfs
> 	tst-syscall1.out
> 	tst-syscall0.out
> 	stdarg
> 	tst-preadvwritev
> 	tst-syscall6.out
> 	tst-mkostemps
> 	Makefile.in
> 	tst-utmp.out
> 	tst-nftw
> 	opendir-tst1.out
> 	tst-syscall1
> 	bug-readdir1.out
> 	tst-hasmntopt
> 	tst-syscall6
> 	fdopen
> 	seek
> 	tst-nftw.out
> 	dirent64
> 	tst-fnmatch.input
> 	tst-utmpx.out
> 	dirent
> 	going back past 4-th entry...
> 	seekdir (d, -1600443765); telldir (d) == -1
> [...]
> FAIL tst-cancel18 got 1 expected 0
> 	going to cancel in-time
> 	Timed out: killed the child process
> [...]
> FAIL tst-cancelx18 got 1 expected 0
> 	going to cancel in-time
> 	Timed out: killed the child process
> [...]
> FAIL tst-tls3 got 1 expected 0
> 
> 	/usr/lib/uclibc-ng-test/test/tls/tst-tls3: symbol 'baz': can't handle reloc type 0x404
> FAIL tst-tls4 got 1 expected 0
> 
> 	/usr/lib/uclibc-ng-test/test/tls/tst-tls4: symbol 'foo': can't handle reloc type 0x404
> FAIL tst-tls5 got 1 expected 0
> 
> 	/usr/lib/uclibc-ng-test/test/tls/tst-tls5: symbol 'foo': can't handle reloc type 0x404
> FAIL tst-tls6 got 1 expected 0
> 
> 	/usr/lib/uclibc-ng-test/test/tls/tst-tls6: symbol 'foo': can't handle reloc type 0x404
> FAIL tst-tls7 got 1 expected 0
> 
> 	/usr/lib/uclibc-ng-test/test/tls/tst-tls7: symbol 'foo': can't handle reloc type 0x404
> FAIL tst-tls8 got 1 expected 0
> 
> 	/usr/lib/uclibc-ng-test/test/tls/tst-tls8: symbol 'foo': can't handle reloc type 0x404
> [...]
> Total skipped: 15
> Total failed: 12
> Total passed: 454
> 
> 
> The tst-res Segmentation fault failure can be fixed by
> this additional uclibc patch:
> 
> --- a/include/resolv.h
> +++ b/include/resolv.h
> @@ -457,7 +457,7 @@ __END_DECLS
>  #    ifndef NOT_IN_libc
>  #     define __resp __libc_resp
>  #    endif
> -#    define _res (*__resp)
> +#    define _res (*__res_state())
>  extern __thread struct __res_state *__resp attribute_tls_model_ie;
>  #   endif
>  #  else
> 
> 
> Will take a look at some glibc resolv tests and try to port
> them (and, if I find enough time, at some of the other
> failures)...

Can you sent the two existing patches with your SoB Line added?

best regards
 Waldemar
Peter Seiderer Nov. 25, 2021, 8:26 p.m. UTC | #5
Hello Waldemar,

On Thu, 11 Nov 2021 09:58:07 +0100, Waldemar Brodkorb <wbx@openadk.org> wrote:

> Hi Peter,
> Peter Seiderer wrote,
>
> > Hello Waldemar,
> >
> > On Sun, 31 Oct 2021 00:56:56 +0200, Waldemar Brodkorb <wbx@openadk.org> wrote:
> >
> > > Hi Peter,
> > > Peter Seiderer wrote,
> > >
> > > > Hello Waldemar, *,
> > > >
> > > > On Mon, 25 Oct 2021 23:25:41 +0200, Peter Seiderer <ps.report@gmx.net> wrote:
> > > >
> > > > The resulting ntpd runs fine with the raspberrypi3_defconfig, but segfaults
> > > > when compiled/used with raspberrypi3_64_defconfig (uclibc, -Os):
> > > >
> > > > 	$ /usr/sbin/ntpd -n -d -g
> > > > 1970-01-01T00:04:18 ntpd[263]: INIT: ntpd ntpsec-1.2.0 2021-10-24T13:39:21Z: Starting
> > > > 1970-01-01T00:04:18 ntpd[263]: INIT: Command line: /usr/sbin/ntpd -n -d
> > > > 1970-01-01T00:04:18 ntpd[263]: INIT: precision = 7.291 usec (-17)
> > > > 1970-01-01T00:04:18 ntpd[263]: INIT: successfully locked into RAM
> > > > 1970-01-01T00:04:18 ntpd[263]: CONFIG: readconfig: parsing file: /etc/ntp.conf
> > > > 1970-01-01T00:04:18 ntpd[263]: CONFIG: restrict nopeer ignored
> > > > 1970-01-01T00:04:18 ntpd[263]: INIT: Using SO_TIMESTAMPNS
> > > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 0 v6wildcard [::]:123
> > > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen and drop on 1 v4wildcard 0.0.0.0:123
> > > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 2 lo 127.0.0.1:123
> > > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 3 eth0 172.16.0.30:123
> > > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 4 lo [::1]:123
> > > > 1970-01-01T00:04:18 ntpd[263]: IO: Listen normally on 5 eth0 [fe80::ba27:ebff:fea6:340%2]:123
> > > > 1970-01-01T00:04:18 ntpd[263]: IO: Listening on routing socket on fd #22 for interface updates
> > > > 1970-01-01T00:04:19 ntpd[263]: SYNC: Found 10 servers, suggest minsane at least 3
> > > > 1970-01-01T00:04:19 ntpd[263]: INIT: MRU 10922 entries, 13 hash bits, 65536 bytes
> > > > 1970-01-01T00:04:20 ntpd[263]: DNS: dns_probe: 0.pool.ntp.org, cast_flags:8, flags:101
> > > > Segmentation fault (core dumped)
> > >
> > > Could you add a small C test program to uClibc-ng-test to trigger
> > > the bug? That would help to find any regression to targets without
> > > TLS support.
> >
> > Did take a first look at the uClibc-ng-test regarding the problem,
> > there is already one test/inet/tst-res test...
> >
> >
> > For the raspberrypi3_defconfig case (uclibc unpatched):
> >
> > 	$ sh uclibcng-testrunner.sh
> > [...]
> > FAIL tst-ethers-line got 1 expected 0
> > 	Cannot open file /etc/ethers: No such file or directory
> > FAIL tst-ethers got 1 expected 0
> > 	Either /etc/ethers is missing or it has incorrect contents
> > [...]
> > FAIL tst-cancel18 got 1 expected 0
> > 	going to cancel in-time
> > 	Timed out: killed the child process
> > [...]
> > FAIL tst-cancelx18 got 1 expected 0
> > 	going to cancel in-time
> > 	Timed out: killed the child process
> > [...]
> > Total skipped: 15
> > Total failed: 4
> > Total passed: 460
> >
> >
> >
> > For the raspberrypi3_64_defconfig case (uclibc unpatched):
> >
> > 	$ sh uclibcng-testrunner.sh
> > [...]
> > FAIL tst-ethers-line got 1 expected 0
> > 	Cannot open file /etc/ethers: No such file or directory
> > FAIL tst-ethers got 1 expected 0
> > 	Either /etc/ethers is missing or it has incorrect contents
> > [...]
> > FAIL tst-res got 139 expected 0
> > 	Segmentation fault (core dumped)
> > [...]
> > FAIL tst-seekdir got 1 expected 0
> > 	.
> > 	..
> > 	tst-seekdir.out
> > 	tst-utmpx
> > 	tst-inotify
> > 	tst-mkostemps.out
> > 	seek.out
> > 	tst-scandir
> > 	tst-seekdir
> > 	tst-statvfs.out
> > 	sem
> > 	stdarg.out
> > 	fdopen.out
> > 	tst-utmp
> > 	tst-preadvwritev.out
> > 	bug-glob2.out
> > 	popen
> > 	dirent64.out
> > 	tst-scandir.out
> > 	tst-hasmntopt.out
> > 	tst-statvfs
> > 	bug-glob2
> > 	popen.out
> > 	Makefile
> > 	opendir-tst1
> > 	sem.out
> > 	tst-inotify.out
> > 	tst-syscall0
> > 	tst-statfs.out
> > 	bug-readdir1
> > 	dirent.out
> > 	tst-statfs
> > 	tst-syscall1.out
> > 	tst-syscall0.out
> > 	stdarg
> > 	tst-preadvwritev
> > 	tst-syscall6.out
> > 	tst-mkostemps
> > 	Makefile.in
> > 	tst-utmp.out
> > 	tst-nftw
> > 	opendir-tst1.out
> > 	tst-syscall1
> > 	bug-readdir1.out
> > 	tst-hasmntopt
> > 	tst-syscall6
> > 	fdopen
> > 	seek
> > 	tst-nftw.out
> > 	dirent64
> > 	tst-fnmatch.input
> > 	tst-utmpx.out
> > 	dirent
> > 	going back past 4-th entry...
> > 	seekdir (d, -1600443765); telldir (d) == -1
> > [...]
> > FAIL tst-cancel18 got 1 expected 0
> > 	going to cancel in-time
> > 	Timed out: killed the child process
> > [...]
> > FAIL tst-cancelx18 got 1 expected 0
> > 	going to cancel in-time
> > 	Timed out: killed the child process
> > [...]
> > FAIL tst-tls3 got 1 expected 0
> >
> > 	/usr/lib/uclibc-ng-test/test/tls/tst-tls3: symbol 'baz': can't handle reloc type 0x404
> > FAIL tst-tls4 got 1 expected 0
> >
> > 	/usr/lib/uclibc-ng-test/test/tls/tst-tls4: symbol 'foo': can't handle reloc type 0x404
> > FAIL tst-tls5 got 1 expected 0
> >
> > 	/usr/lib/uclibc-ng-test/test/tls/tst-tls5: symbol 'foo': can't handle reloc type 0x404
> > FAIL tst-tls6 got 1 expected 0
> >
> > 	/usr/lib/uclibc-ng-test/test/tls/tst-tls6: symbol 'foo': can't handle reloc type 0x404
> > FAIL tst-tls7 got 1 expected 0
> >
> > 	/usr/lib/uclibc-ng-test/test/tls/tst-tls7: symbol 'foo': can't handle reloc type 0x404
> > FAIL tst-tls8 got 1 expected 0
> >
> > 	/usr/lib/uclibc-ng-test/test/tls/tst-tls8: symbol 'foo': can't handle reloc type 0x404
> > [...]
> > Total skipped: 15
> > Total failed: 12
> > Total passed: 454
> >
> >
> > The tst-res Segmentation fault failure can be fixed by
> > this additional uclibc patch:
> >
> > --- a/include/resolv.h
> > +++ b/include/resolv.h
> > @@ -457,7 +457,7 @@ __END_DECLS
> >  #    ifndef NOT_IN_libc
> >  #     define __resp __libc_resp
> >  #    endif
> > -#    define _res (*__resp)
> > +#    define _res (*__res_state())
> >  extern __thread struct __res_state *__resp attribute_tls_model_ie;
> >  #   endif
> >  #  else
> >
> >
> > Will take a look at some glibc resolv tests and try to port
> > them (and, if I find enough time, at some of the other
> > failures)...
>
> Can you sent the two existing patches with your SoB Line added?

And finally done (sorry for the delay):

	https://patchwork.ozlabs.org/project/uclibc-ng/patch/20211125201825.22354-1-ps.report@gmx.net/

Regards,
Peter

>
> best regards
>  Waldemar
>
diff mbox series

Patch

diff --git a/DEVELOPERS b/DEVELOPERS
index 771519fd9b..593526e61f 100644
--- a/DEVELOPERS
+++ b/DEVELOPERS
@@ -2167,6 +2167,7 @@  F:	package/iwd/
 F:	package/libevdev/
 F:	package/libuev/
 F:	package/log4cplus/
+F:	package/ntpsec/
 F:	package/postgresql/
 F:	package/python-colorzero/
 F:	package/python-flask-wtf/
diff --git a/package/Config.in b/package/Config.in
index d40eb9dabc..842e555342 100644
--- a/package/Config.in
+++ b/package/Config.in
@@ -2256,6 +2256,7 @@  endif
 	source "package/nmap/Config.in"
 	source "package/noip/Config.in"
 	source "package/ntp/Config.in"
+	source "package/ntpsec/Config.in"
 	source "package/nuttcp/Config.in"
 	source "package/odhcp6c/Config.in"
 	source "package/odhcploc/Config.in"
diff --git a/package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch b/package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch
new file mode 100644
index 0000000000..c2838fe8e0
--- /dev/null
+++ b/package/ntpsec/0001-ntptime-fix-jfmt5-ofmt5-jfmt6-ofmt6-related-compile-.patch
@@ -0,0 +1,61 @@ 
+From 4015a1183d2f79dad6dd675ca5e0d329825f3fa3 Mon Sep 17 00:00:00 2001
+From: Peter Seiderer <ps.report@gmx.net>
+Date: Mon, 4 Oct 2021 22:25:58 +0200
+Subject: [PATCH] ntptime: fix jfmt5/ofmt5 jfmt6/ofmt6 related compile failure
+MIME-Version: 1.0
+Content-Type: text/plain; charset=UTF-8
+Content-Transfer-Encoding: 8bit
+
+Use same define guard for definiton as for usage ('HAVE_STRUCT_NTPTIMEVAL_TAI'
+instead of 'NTP_API && NTP_API > 3').
+
+Fixes:
+
+  ../../ntptime/ntptime.c: In function ‘main’:
+  ../../ntptime/ntptime.c:349:17: error: ‘jfmt5’ undeclared (first use in this function); did you mean ‘jfmt6’?
+    349 |   printf(json ? jfmt5 : ofmt5, (long)ntv.tai);
+        |                 ^~~~~
+        |                 jfmt6
+  ../../ntptime/ntptime.c:349:17: note: each undeclared identifier is reported only once for each function it appears in
+  ../../ntptime/ntptime.c:349:25: error: ‘ofmt5’ undeclared (first use in this function); did you mean ‘ofmt6’?
+    349 |   printf(json ? jfmt5 : ofmt5, (long)ntv.tai);
+        |                         ^~~~~
+        |                         ofmt6
+  ../../ntptime/ntptime.c:321:15: warning: unused variable ‘jfmt6’ [-Wunused-variable]
+    321 |   const char *jfmt6 = "";
+        |               ^~~~~
+  ../../ntptime/ntptime.c:311:15: warning: unused variable ‘ofmt6’ [-Wunused-variable]
+    311 |   const char *ofmt6 = "\n";
+        |               ^~~~~
+
+[Upstream: https://gitlab.com/NTPsec/ntpsec/-/merge_requests/1245]
+Signed-off-by: Peter Seiderer <ps.report@gmx.net>
+---
+ ntptime/ntptime.c | 4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+diff --git a/ntptime/ntptime.c b/ntptime/ntptime.c
+index ff861cb..5d58593 100644
+--- a/ntptime/ntptime.c
++++ b/ntptime/ntptime.c
+@@ -305,7 +305,7 @@ main(
+ 		const char *ofmt2 = "  time %s, (.%0*d),\n";
+ 		const char *ofmt3 = "  maximum error %lu us, estimated error %lu us";
+ 		const char *ofmt4 = "  ntptime=%x.%x unixtime=%x.%0*d %s";
+-#if defined NTP_API && NTP_API > 3
++#if defined(HAVE_STRUCT_NTPTIMEVAL_TAI)
+ 		const char *ofmt5 = ", TAI offset %ld\n";
+ #else
+ 		const char *ofmt6 = "\n";
+@@ -315,7 +315,7 @@ main(
+ 		const char *jfmt2 = "\"time\":\"%s\",\"fractional-time\":\".%0*d\",";
+ 		const char *jfmt3 = "\"maximum-error\":%lu,\"estimated-error\":%lu,";
+ 		const char *jfmt4 = "\"raw-ntp-time\":\"%x.%x\",\"raw-unix-time\":\"%x.%0*d %s\",";
+-#if defined NTP_API && NTP_API > 3
++#if defined(HAVE_STRUCT_NTPTIMEVAL_TAI)
+ 		const char *jfmt5 = "\"TAI-offset\":%d,";
+ #else
+ 		const char *jfmt6 = "";
+-- 
+2.33.0
+
diff --git a/package/ntpsec/Config.in b/package/ntpsec/Config.in
new file mode 100644
index 0000000000..7275533d26
--- /dev/null
+++ b/package/ntpsec/Config.in
@@ -0,0 +1,31 @@ 
+config BR2_PACKAGE_NTPSEC
+	bool "ntpsec"
+	depends on BR2_PACKAGE_PYTHON3
+	select BR2_PACKAGE_LIBCAP
+	select BR2_PACKAGE_OPENSSL
+	help
+	  NTPsec project - a secure, hardened, and improved
+	  implementation of Network Time Protocol derived
+	  from NTP Classic, Dave Mills’s original.
+
+	  Provides things like ntpd, ntpdate, ntpq, etc...
+
+	  https://www.ntpsec.org/
+
+if BR2_PACKAGE_NTPSEC
+
+config BR2_PACKAGE_NTPSEC_CLASSIC_MODE
+	bool "classic-mode"
+	help
+	  Enable strict configuration and log-format compatibility
+	  with NTP Classic.
+
+config BR2_PACKAGE_NTPSEC_NTS
+	bool "NTS support"
+	help
+	  Enable Network Time Security (NTS) support.
+
+endif
+
+comment "ntpsec depens on Pyhton3"
+	depends on !BR2_PACKAGE_PYTHON3
diff --git a/package/ntpsec/S49ntp b/package/ntpsec/S49ntp
new file mode 100644
index 0000000000..f3db51418e
--- /dev/null
+++ b/package/ntpsec/S49ntp
@@ -0,0 +1,58 @@ 
+#!/bin/sh
+#
+# Starts Network Time Protocol daemon
+#
+
+DAEMON="ntpd"
+PIDFILE="/var/run/$DAEMON.pid"
+
+NTPD_ARGS="-g -u ntp:ntp -s /var/run/ntp"
+
+# shellcheck source=/dev/null
+[ -r "/etc/default/$DAEMON" ] && . "/etc/default/$DAEMON"
+
+mkdir -p /var/run/ntp && chown ntp:ntp /var/run/ntp
+
+start() {
+	printf 'Starting %s: ' "$DAEMON"
+	# shellcheck disable=SC2086 # we need the word splitting
+	start-stop-daemon -S -q -p "$PIDFILE" -x "/usr/sbin/$DAEMON" \
+		-- $NTPD_ARGS -p "$PIDFILE"
+	status=$?
+	if [ "$status" -eq 0 ]; then
+		echo "OK"
+	else
+		echo "FAIL"
+	fi
+	return "$status"
+}
+
+stop() {
+	printf 'Stopping %s: ' "$DAEMON"
+	start-stop-daemon -K -q -p "$PIDFILE"
+	status=$?
+	if [ "$status" -eq 0 ]; then
+		rm -f "$PIDFILE"
+		echo "OK"
+	else
+		echo "FAIL"
+	fi
+	return "$status"
+}
+
+restart() {
+	stop
+	sleep 1
+	start
+}
+
+case "$1" in
+	start|stop|restart)
+		"$1";;
+	reload)
+		# Restart, since there is no true "reload" feature.
+		restart;;
+	*)
+		echo "Usage: $0 {start|stop|restart|reload}"
+		exit 1
+esac
diff --git a/package/ntpsec/ntpd.etc.conf b/package/ntpsec/ntpd.etc.conf
new file mode 100644
index 0000000000..e0f45c1438
--- /dev/null
+++ b/package/ntpsec/ntpd.etc.conf
@@ -0,0 +1,33 @@ 
+#
+# legacy NTP configuration
+#
+pool 0.pool.ntp.org iburst
+pool 1.pool.ntp.org iburst
+pool 2.pool.ntp.org iburst
+pool 3.pool.ntp.org iburst
+
+#
+# NTS configuration
+#
+# Notes:
+#  - uncomment the following lines to enable NTS support (but
+#    make sure the initial clock is up-to-date (otherwise the
+#    NTS certificate validation will fail with 'NTSc: certificate invalid:
+#    9=>certificate is not yet valid' as on boards without RTC support)
+#    and/or keep at least one line from the legacy NTP lines
+#  - enable BR2_PACKAGE_CA_CERTIFICATES to gain access to the certificate
+#    files
+#
+# server time.cloudflare.com nts  # Global, anycast
+# server nts.ntp.se:4443 nts      # Sweden
+# server ntpmon.dcs1.biz nts      # Singapore
+# server ntp1.glypnod.com nts     # San Francisco
+# server ntp2.glypnod.com nts     # London
+#
+# ca /usr/share/ca-certificates/mozilla
+
+# Allow only time queries, at a limited rate, sending KoD when in excess.
+# Allow all local queries (IPv4, IPv6)
+restrict default nomodify nopeer noquery limited kod
+restrict 127.0.0.1
+restrict [::1]
diff --git a/package/ntpsec/ntpsec.hash b/package/ntpsec/ntpsec.hash
new file mode 100644
index 0000000000..9c30605cbd
--- /dev/null
+++ b/package/ntpsec/ntpsec.hash
@@ -0,0 +1,4 @@ 
+# Locally calculated
+sha256  80e5b4c07dc1f8f7dc90851662c72a80a4111477c48040ae9e1f2e56f893251d  ntpsec-NTPsec_1_2_0.tar.bz2
+sha256  b4db4de3317c3b0554ed91eb692968800bdfd6ad2c16ffbeee8ce4895ed91da4  LICENSE.adoc
+sha256  d3b21470adadd9abd9c6d675378f8c371ac5a4ea6dbec91859e02fadca3c0856  docs/copyright.adoc
diff --git a/package/ntpsec/ntpsec.mk b/package/ntpsec/ntpsec.mk
new file mode 100644
index 0000000000..c62077dce6
--- /dev/null
+++ b/package/ntpsec/ntpsec.mk
@@ -0,0 +1,71 @@ 
+################################################################################
+#
+# ntpsec
+#
+################################################################################
+
+NTPSEC_VERSION_MAJOR = 1
+NTPSEC_VERSION_MINOR = 2
+NTPSEC_VERSION_POINT = 0
+NTPSEC_VERSION = $(NTPSEC_VERSION_MAJOR)_$(NTPSEC_VERSION_MINOR)_$(NTPSEC_VERSION_POINT)
+NTPSEC_SOURCE = ntpsec-NTPsec_$(NTPSEC_VERSION).tar.bz2
+NTPSEC_SITE = https://gitlab.com/NTPsec/ntpsec/-/archive/NTPsec_$(NTPSEC_VERSION)
+NTPSEC_LICENSE = BSD-2-Clause NTP BSD-3-Clause MIT
+NTPSEC_LICENSE_FILES = LICENSE.adoc docs/copyright.adoc
+
+NTPSEC_CPE_ID_VENDOR = ntpsec
+NTPSEC_CPE_ID_VERSION = $(NTPSEC_VERSION_MAJOR).$(NTPSEC_VERSION_MINOR)
+NTPSEC_CPE_ID_UPDATE = $(NTPSEC_VERSION_POINT)
+
+NTPSEC_DEPENDENCIES = \
+	host-pkgconf \
+	$(if $(BR2_PACKAGE_PYTHON),python,python3) \
+	libcap \
+	openssl
+
+NTPSEC_CONF_OPTS = \
+	CC=gcc \
+	PYTHON_CONFIG="$(STAGING_DIR)/usr/bin/$(if $(BR2_PACKAGE_PYTHON),python,python3)-config" \
+	--cross-compiler="$(TARGET_CC)" \
+	--cross-cflags="$(TARGET_CFLAGS) -std=gnu99" \
+	--cross-ldflags="$(TARGET_LDFLAGS)" \
+	--notests \
+	--enable-early-droproot \
+	--disable-mdns-registration \
+	--enable-pylib=ffi \
+	--nopyc \
+	--nopyo \
+	--nopycache \
+	--disable-doc \
+	--disable-manpage
+
+ifeq ($(BR2_PACKAGE_NTPSEC_CLASSIC_MODE),y)
+NTPSEC_CONF_OPTS += --enable-classic-mode
+endif
+
+ifeq ($(BR2_PACKAGE_NTPSEC_NTS),y)
+#NTPSEC_CONF_OPTS += --enable-nts
+else
+NTPSEC_CONF_OPTS += --disable-nts
+endif
+
+# add a link to libntpc.so where python searches for it
+define NTPSEC_LIBNTPC_LINK
+	ln -sf /usr/lib/ntp/libntpc.so $(TARGET_DIR)/usr/lib/libntpc.so
+endef
+NTPSEC_POST_INSTALL_TARGET_HOOKS += NTPSEC_LIBNTPC_LINK
+
+define NTPSEC_INSTALL_NTPSEC_CONF
+	$(INSTALL) -m 644 package/ntpsec/ntpd.etc.conf $(TARGET_DIR)/etc/ntp.conf
+endef
+NTPSEC_POST_INSTALL_TARGET_HOOKS += NTPSEC_INSTALL_NTPSEC_CONF
+
+define NTPSEC_INSTALL_INIT_SYSV
+	$(INSTALL) -D -m 755 package/ntpsec/S49ntp $(TARGET_DIR)/etc/init.d/S49ntp
+endef
+
+define NTPSEC_USERS
+	ntp -1 ntp -1 * - - - ntpd user
+endef
+
+$(eval $(waf-package))