summaryrefslogtreecommitdiff
path: root/test
diff options
context:
space:
mode:
Diffstat (limited to 'test')
-rwxr-xr-xtest/compilation/001-features4
-rwxr-xr-xtest/compilation/003-sanitizers87
-rwxr-xr-xtest/simulation/101-poll4
-rwxr-xr-xtest/simulation/106-refclock15
-rwxr-xr-xtest/simulation/108-peer21
-rwxr-xr-xtest/simulation/110-chronyc74
-rwxr-xr-xtest/simulation/121-orphan1
-rwxr-xr-xtest/simulation/126-burst16
-rwxr-xr-xtest/simulation/127-filter19
-rwxr-xr-xtest/simulation/128-nocontrol25
-rwxr-xr-xtest/simulation/129-reload25
-rwxr-xr-xtest/simulation/130-quit23
-rwxr-xr-xtest/simulation/131-maxchange20
-rwxr-xr-xtest/simulation/132-logchange21
-rwxr-xr-xtest/simulation/133-hwtimestamp32
-rw-r--r--test/simulation/test.common44
-rw-r--r--test/unit/clientlog.c4
-rw-r--r--test/unit/hash.c2
-rw-r--r--test/unit/hwclock.c82
-rw-r--r--test/unit/ntp_core.c55
-rw-r--r--test/unit/ntp_core.keys6
-rw-r--r--test/unit/samplefilt.c113
-rw-r--r--test/unit/sources.c31
-rw-r--r--test/unit/test.c10
-rw-r--r--test/unit/test.h3
-rw-r--r--test/unit/util.c70
26 files changed, 717 insertions, 90 deletions
diff --git a/test/compilation/001-features b/test/compilation/001-features
index d61c07f..125ed31 100755
--- a/test/compilation/001-features
+++ b/test/compilation/001-features
@@ -4,6 +4,8 @@
cd ../..
+export CFLAGS="-O2 -Werror -Wpointer-arith -Wformat-signedness -Wno-unknown-warning-option -D_FORTIFY_SOURCE=2"
+
for opts in \
"--enable-debug" \
"--enable-ntp-signd" \
@@ -23,6 +25,6 @@ for opts in \
"--disable-cmdmon --disable-refclock" \
"--disable-cmdmon --disable-ntp --disable-refclock"
do
- ./configure $opts
+ ./configure $opts || exit 1
make "$@" || exit 1
done
diff --git a/test/compilation/003-sanitizers b/test/compilation/003-sanitizers
new file mode 100755
index 0000000..54f0a87
--- /dev/null
+++ b/test/compilation/003-sanitizers
@@ -0,0 +1,87 @@
+#!/bin/bash
+# Run the unit and simulation tests with different compiler sanitizers
+# and under valgrind
+
+cd ../..
+
+if [ "$(uname -sm)" != "Linux x86_64" ]; then
+ echo Test supported on Linux x86_64 only
+ exit 1
+fi
+
+[ -f /etc/os-release ] && . /etc/os-release
+
+if [ "$ID" = "fedora" ]; then
+ echo Checking test dependencies:
+ rpm -q {valgrind,gcc,clang}.x86_64 {libgcc,clang-libs}.{x86_64,i686} || exit 1
+ rpm -q {libseccomp,nettle,nss-softokn-freebl,libtomcrypt}-devel.{x86_64,i686} || exit 1
+ echo
+fi
+
+touch Makefile
+
+for CC in gcc clang; do
+ export CC
+
+ for arch_opts in "-m32" ""; do
+ pushd test/simulation/clknetsim || exit 1
+ make clean > /dev/null 2>&1
+ CFLAGS="$arch_opts -DCLKNETSIM_DISABLE_SYSCALL" make "$@" || exit 1
+ echo
+
+ popd
+
+ for extra_config_opts in \
+ "--all-privops" \
+ "--disable-scfilter" \
+ "--without-nettle" \
+ "--without-nettle --without-nss" \
+ "--without-nettle --without-nss --without-tomcrypt"; \
+ do
+ for san_options in "" "-fsanitize=address" "-fsanitize=memory"; do
+ export CFLAGS="-O2 -g -fsanitize=undefined -fsanitize=float-divide-by-zero -fno-sanitize-recover=undefined,float-divide-by-zero $san_options $arch_opts"
+
+ # clang msan doesn't work on i686 and otherwise requires patches
+ echo $CFLAGS | grep -q 'sanitize=memory' && continue
+
+ # build fails with clang ubsan on i686 (Fedora only?)
+ [ "$arch_opts" = "-m32" -a "$CC" = "clang" ] && continue
+
+ [ "$CC" = "gcc" ] && echo $CFLAGS | grep -q 'sanitize=address' && CFLAGS="$CFLAGS -static-libasan"
+
+ config_opts="--with-user=chrony --enable-debug --enable-scfilter --enable-ntp-signd $extra_config_opts"
+
+ echo -----------------------------------------------------------------------------
+ echo CC=\"$CC\" CFLAGS=\"$CFLAGS\" ./configure $config_opts
+
+ make distclean > /dev/null 2>&1
+
+ ./configure $config_opts || exit 1
+
+ if echo "$config_opts" | grep -q all-privops; then
+ for op in ADJUSTTIME ADJUSTTIMEX SETTIME BINDSOCKET; do
+ echo "#define PRIVOPS_$op 1" >> config.h
+ done
+ fi
+
+ make "$@" || exit 1
+
+ [ -n "$BUILD_TEST_ONLY" ] && continue
+
+ echo
+ pushd test/unit || exit 1
+ if [ "$san_options" = "" ]; then
+ make check TEST_WRAPPER="valgrind --error-exitcode=1" || exit 1
+ else
+ make check || exit 1
+ fi
+ popd
+
+ echo
+ pushd test/simulation || exit 1
+ CLKNETSIM_RANDOM_SEED=101 ./run -i 1 || exit 1
+ popd
+ done
+ done
+ done
+done
diff --git a/test/simulation/101-poll b/test/simulation/101-poll
index f350777..cb3647f 100755
--- a/test/simulation/101-poll
+++ b/test/simulation/101-poll
@@ -12,11 +12,13 @@ time_rms_limit=5e-6
freq_rms_limit=5e-6
client_conf="makestep 1e-2 1"
-for poll in $(seq 2 14); do
+for poll in $(seq 1 14); do
client_server_options="minpoll $poll maxpoll $poll"
limit=$[2**$poll * 10]
min_sync_time=$[2**$poll * 2]
max_sync_time=$[2**$poll * 21 / 10 + 1]
+ client_max_min_out_interval=$(awk "BEGIN {print 2^$poll * 1.1}")
+ client_min_mean_out_interval=$(awk "BEGIN {print 2^$poll * 0.99}")
run_test || test_fail
check_chronyd_exit || test_fail
diff --git a/test/simulation/106-refclock b/test/simulation/106-refclock
index c22cd42..5c5794c 100755
--- a/test/simulation/106-refclock
+++ b/test/simulation/106-refclock
@@ -9,19 +9,22 @@ refclock_jitter=$jitter
min_sync_time=45
max_sync_time=70
chronyc_start=70
-client_conf="refclock SHM 0 stratum 3 delay 1e-3 refid GPS"
chronyc_conf="tracking"
-run_test || test_fail
-check_chronyd_exit || test_fail
-check_source_selection || test_fail
-check_sync || test_fail
-check_chronyc_output "^Reference ID.*47505300 \(GPS\)
+for refclock in "SHM 0" "PHC /dev/ptp0"; do
+ client_conf="refclock $refclock stratum 3 delay 1e-3 refid GPS"
+
+ run_test || test_fail
+ check_chronyd_exit || test_fail
+ check_source_selection || test_fail
+ check_sync || test_fail
+ check_chronyc_output "^Reference ID.*47505300 \(GPS\)
Stratum.*: 4
.*
Root delay : 0.001000000 seconds
.*
Update interval : 16\.. seconds
.*$" || test_fail
+done
test_pass
diff --git a/test/simulation/108-peer b/test/simulation/108-peer
index 0679f6e..20e2254 100755
--- a/test/simulation/108-peer
+++ b/test/simulation/108-peer
@@ -30,4 +30,25 @@ check_chronyd_exit || test_fail
check_source_selection || test_fail
check_sync || test_fail
+base_delay="(+ 1e-4 (* -1 (equal 0.1 from 3) (equal 0.1 to 1)))"
+client_peer_options=""
+
+while read lminpoll lmaxpoll rminpoll rmaxpoll max_sync_time; do
+ client_lpeer_options="minpoll $lminpoll maxpoll $lmaxpoll"
+ client_rpeer_options="minpoll $rminpoll maxpoll $rmaxpoll"
+ limit=$[$max_sync_time * 10]
+
+ run_test || test_fail
+ check_chronyd_exit || test_fail
+ check_sync || test_fail
+done <<-EOF
+ 3 6 3 6 400
+ 3 3 6 6 450
+ 6 6 3 3 450
+ 3 6 6 6 450
+ 6 6 3 6 450
+ -2 -2 2 2 220
+ 2 2 -2 -2 220
+EOF
+
test_pass
diff --git a/test/simulation/110-chronyc b/test/simulation/110-chronyc
index d56e724..944cf3f 100755
--- a/test/simulation/110-chronyc
+++ b/test/simulation/110-chronyc
@@ -63,4 +63,78 @@ try: 1, refid: C0A87B01, correction: 0\.000......, skew: .\....
513 RTC driver not running$" \
|| test_fail
+server_strata=0
+chronyc_start=0
+client_conf=""
+limit=1
+
+for chronyc_conf in \
+ "accheck 1.2.3.4" \
+ "add peer 10.0.0.0 minpoll 2 maxpoll 6" \
+ "add server 10.0.0.0 minpoll 6 maxpoll 10 iburst burst key 1 maxdelay 1e-3 maxdelayratio 10.0 maxdelaydevratio 10.0 mindelay 1e-4 asymmetry 0.5 offset 1e-5 minsamples 6 maxsamples 6 filter 3 offline auto_offline prefer noselect trust require xleave polltarget 20 port 123 presend 7 minstratum 3 version 4" \
+ "allow 1.2.3.4" \
+ "allow 1.2" \
+ "allow 3.4.5" \
+ "allow 6.7.8/22" \
+ "allow 6.7.8.9/22" \
+ "allow 2001:db8::/32" \
+ "allow 0/0" \
+ "allow ::/0" \
+ "allow" \
+ "allow all 10/24" \
+ "burst 5/10" \
+ "burst 3/5 255.255.255.0/1.2.3.0" \
+ "burst 1/2 1.2.3.0/24" \
+ "clients" \
+ "cmdaccheck 1.2.3.4" \
+ "cmdallow 1.2.3.4" \
+ "cmdallow all 1.2.3.0/24" \
+ "cmddeny 1.2.3.4" \
+ "cmddeny all 1.2.3.0/24" \
+ "cyclelogs" \
+ "delete 10.0.0.0" \
+ "deny 1.2.3.4" \
+ "deny all 1.2.3.0/24" \
+ "dump" \
+ "local stratum 5 distance 1.0 orphan" \
+ "local off" \
+ "makestep 10.0 3" \
+ "makestep" \
+ "manual delete 0" \
+ "manual off" \
+ "manual on" \
+ "manual reset" \
+ "maxdelay 1.2.3.4 1e-2" \
+ "maxdelaydevratio 1.2.3.4 5.0" \
+ "maxdelayratio 1.2.3.4 3.0" \
+ "maxpoll 1.2.3.4 5" \
+ "maxupdateskew 1.2.3.4 10.0" \
+ "minpoll 1.2.3.4 3" \
+ "minstratum 1.2.3.4 1" \
+ "ntpdata 1.2.3.4" \
+ "offline" \
+ "offline 255.255.255.0/1.2.3.0" \
+ "offline 1.2.3.0/24" \
+ "online" \
+ "online 1.2.3.0/24" \
+ "onoffline" \
+ "polltarget 1.2.3.4 10" \
+ "refresh" \
+ "rekey" \
+ "reselect" \
+ "reselectdist 1e-3" \
+ "settime 16:30" \
+ "settime 16:30:05" \
+ "settime Nov 21, 2015 16:30:05" \
+ "shutdown" \
+ "smoothtime reset" \
+ "smoothtime activate" \
+ "trimrtc" \
+ "writertc"
+do
+ run_test || test_fail
+ check_chronyd_exit || test_fail
+ check_chronyc_output "501 Not authorised" || test_fail
+done
+
test_pass
diff --git a/test/simulation/121-orphan b/test/simulation/121-orphan
index ed92153..1b47f76 100755
--- a/test/simulation/121-orphan
+++ b/test/simulation/121-orphan
@@ -10,6 +10,7 @@ server 192.168.123.1
server 192.168.123.2
server 192.168.123.3"
max_sync_time=500
+client_start=140
chronyc_start=300
chronyc_conf="tracking"
time_rms_limit=5e-4
diff --git a/test/simulation/126-burst b/test/simulation/126-burst
index 3173c78..d63f290 100755
--- a/test/simulation/126-burst
+++ b/test/simulation/126-burst
@@ -26,4 +26,20 @@ check_source_selection || test_fail
check_packet_interval || test_fail
check_sync || test_fail
+# Add a significant delay to 70% of packets on the 2->1 path after 6th packet
+base_delay=$(cat <<-EOF | tr -d '\n'
+ (+ 1e-4
+ (* 0.15
+ (equal 0.1 from 2)
+ (equal 0.1 to 1)
+ (equal 0.1 (min (sum 1) 7) 7)
+ (equal 0.7 (uniform) 0.0)))
+EOF
+)
+
+run_test || test_fail
+check_chronyd_exit || test_fail
+check_source_selection || test_fail
+check_packet_interval || test_fail
+
test_pass
diff --git a/test/simulation/127-filter b/test/simulation/127-filter
new file mode 100755
index 0000000..737d1f9
--- /dev/null
+++ b/test/simulation/127-filter
@@ -0,0 +1,19 @@
+#!/bin/bash
+
+. ./test.common
+
+test_start "filter option"
+
+client_server_options="minpoll 4 maxpoll 4 filter 15"
+min_sync_time=710
+max_sync_time=720
+client_max_min_out_interval=16.1
+client_min_mean_out_interval=15.9
+
+run_test || test_fail
+check_chronyd_exit || test_fail
+check_source_selection || test_fail
+check_packet_interval || test_fail
+check_sync || test_fail
+
+test_pass
diff --git a/test/simulation/128-nocontrol b/test/simulation/128-nocontrol
new file mode 100755
index 0000000..0a98cd7
--- /dev/null
+++ b/test/simulation/128-nocontrol
@@ -0,0 +1,25 @@
+#!/bin/bash
+
+. ./test.common
+
+test_start "-x option"
+
+wander=0.0
+time_offset=0.0
+freq_offset=0.0
+time_max_limit=1e-6
+freq_max_limit=1e-9
+min_sync_time=0
+max_sync_time=0
+client_chronyd_options="-x"
+chronyc_start=300
+chronyc_conf="tracking"
+
+run_test || test_fail
+check_chronyd_exit || test_fail
+check_source_selection || test_fail
+check_packet_interval || test_fail
+check_sync || test_fail
+check_chronyc_output "^.*Stratum *: 2.*$" || test_fail
+
+test_pass
diff --git a/test/simulation/129-reload b/test/simulation/129-reload
new file mode 100755
index 0000000..9c4e985
--- /dev/null
+++ b/test/simulation/129-reload
@@ -0,0 +1,25 @@
+#!/bin/bash
+
+. ./test.common
+
+test_start "-r option"
+
+wander=0.0
+limit=100
+min_sync_time=100
+max_sync_time=104
+client_chronyd_options="-r"
+client_conf="dumpdir tmp"
+
+run_test || test_fail
+
+client_start=$limit
+limit=1000
+
+run_test || test_fail
+check_chronyd_exit || test_fail
+check_source_selection || test_fail
+check_packet_interval || test_fail
+check_sync || test_fail
+
+test_pass
diff --git a/test/simulation/130-quit b/test/simulation/130-quit
new file mode 100755
index 0000000..0183885
--- /dev/null
+++ b/test/simulation/130-quit
@@ -0,0 +1,23 @@
+#!/bin/bash
+
+. ./test.common
+
+test_start "-q/-Q option"
+
+wander=0.0
+freq_offset=0.0
+min_sync_time=5
+max_sync_time=10
+client_chronyd_options="-q"
+client_server_options="iburst"
+
+run_test || test_fail
+check_chronyd_exit || test_fail
+check_packet_interval || test_fail
+check_sync || test_fail
+
+client_chronyd_options="-Q"
+run_test || test_fail
+check_sync && test_fail
+
+test_pass
diff --git a/test/simulation/131-maxchange b/test/simulation/131-maxchange
new file mode 100755
index 0000000..969f71f
--- /dev/null
+++ b/test/simulation/131-maxchange
@@ -0,0 +1,20 @@
+#!/bin/bash
+
+. ./test.common
+
+test_start "maxchange directive"
+
+time_offset=2
+max_sync_time=5000
+client_conf="maxchange 0.1 1 3"
+client_step="(* $step (equal 0.1 (sum 1.0) 300))"
+
+run_test || test_fail
+check_chronyd_exit && test_fail
+check_source_selection || test_fail
+check_packet_interval || test_fail
+check_sync && test_fail
+check_log_messages "seconds exceeds.*ignored" 3 3 || test_fail
+check_log_messages "seconds exceeds.*exiting" 1 1 || test_fail
+
+test_pass
diff --git a/test/simulation/132-logchange b/test/simulation/132-logchange
new file mode 100755
index 0000000..ca6244e
--- /dev/null
+++ b/test/simulation/132-logchange
@@ -0,0 +1,21 @@
+#!/bin/bash
+
+. ./test.common
+
+test_start "logchange directive"
+
+time_offset=2
+min_sync_time=600
+max_sync_time=700
+client_server_options="maxsamples 6"
+client_conf="logchange 0.1"
+client_step="(* $step (equal 0.1 (sum 1.0) 300))"
+
+run_test || test_fail
+check_chronyd_exit || test_fail
+check_source_selection || test_fail
+check_packet_interval || test_fail
+check_sync || test_fail
+check_log_messages "clock wrong by" 4 8 || test_fail
+
+test_pass
diff --git a/test/simulation/133-hwtimestamp b/test/simulation/133-hwtimestamp
new file mode 100755
index 0000000..1448c21
--- /dev/null
+++ b/test/simulation/133-hwtimestamp
@@ -0,0 +1,32 @@
+#!/bin/bash
+
+. ./test.common
+
+test_start "hwtimestamp directive"
+
+export CLKNETSIM_TIMESTAMPING=2
+
+refclock_jitter=1e-8
+refclock_offset=10.0
+min_sync_time=4
+max_sync_time=20
+limit=200
+client_conf="hwtimestamp eth0"
+client_server_options="minpoll 0 maxpoll 0 minsamples 32"
+client_chronyd_options="-d"
+
+run_test || test_fail
+check_chronyd_exit || test_fail
+check_source_selection || test_fail
+check_sync || test_fail
+
+if grep -q 'FEAT_DEBUG 1' ../../config.h; then
+ check_log_messages "HW clock samples" 190 200 || test_fail
+ check_log_messages "HW clock reset" 0 0 || test_fail
+ check_log_messages "Received.*tss=1" 1 1 || test_fail
+ check_log_messages "Received.*tss=2" 390 400 || test_fail
+ check_log_messages "update_tx_timestamp.*Updated" 50 140 || test_fail
+ check_log_messages "update_tx_timestamp.*Unacceptable" 50 140 || test_fail
+fi
+
+test_pass
diff --git a/test/simulation/test.common b/test/simulation/test.common
index 0cd0fce..c5758c6 100644
--- a/test/simulation/test.common
+++ b/test/simulation/test.common
@@ -62,7 +62,8 @@ default_client_rpeer_options=""
default_server_conf=""
default_client_conf=""
default_chronyc_conf=""
-default_chronyd_options=""
+default_server_chronyd_options=""
+default_client_chronyd_options=""
default_time_max_limit=1e-3
default_freq_max_limit=5e-4
@@ -75,10 +76,9 @@ default_client_min_mean_out_interval=0.0
default_client_max_min_out_interval=inf
# Initialize test settings from their defaults
-for defopt in $(declare | grep '^default_'); do
- defoptname=${defopt%%=*}
+for defoptname in ${!default_*}; do
optname=${defoptname#default_}
- eval "[ -z \"\${$optname:+a}\" ] && $optname=\"\$$defoptname\""
+ [ -z "${!optname}" ] && declare "$optname"="${!defoptname}"
done
test_start() {
@@ -253,7 +253,7 @@ check_chronyd_exit() {
for i in $(seq 1 $(get_chronyd_nodes)); do
test_message 3 0 "node $i:"
- tail -n 1 tmp/log.$i | grep -q 'chronyd exiting' && \
+ grep -q 'chronyd exiting' tmp/log.$i && \
! grep -q 'Adjustment.*exceeds.*exiting' tmp/log.$i && \
test_ok || test_bad
[ $? -eq 0 ] || ret=1
@@ -337,6 +337,24 @@ check_chronyc_output() {
return $ret
}
+# Check the number of messages matching a matter in the client logs
+check_log_messages() {
+ local i count ret=0 pattern=$1 min=$2 max=$3
+
+ test_message 2 1 "checking number of messages \"$pattern\":"
+
+ for i in $(seq $[$servers * $server_strata + 1] $(get_chronyd_nodes)); do
+ count=$(grep "$pattern" tmp/log.$i | wc -l)
+ test_message 3 0 "node $i: $count"
+
+ [ "$min" -le "$count" ] && [ "$count" -le "$max" ] && \
+ test_ok || test_bad
+ [ $? -eq 0 ] || ret=1
+ done
+
+ return $ret
+}
+
# Check if only NTP port (123) was used
check_packet_port() {
local i ret=0 port=123
@@ -358,14 +376,13 @@ check_packet_port() {
# Print test settings which differ from default value
print_nondefaults() {
- local defopt defoptname optname
+ local defoptname optname
test_message 2 1 "non-default settings:"
- declare | grep '^default_*' | while read defopt; do
- defoptname=${defopt%%=*}
+ for defoptname in ${!default_*}; do
optname=${defoptname#default_}
- eval "[ \"\$$optname\" = \"\$$defoptname\" ]" || \
- test_message 3 1 $(eval "echo $optname=\$$optname")
+ [ "${!defoptname}" = "${!optname}" ] || \
+ test_message 3 1 $optname=${!optname}
done
}
@@ -382,7 +399,7 @@ run_simulation() {
}
run_test() {
- local i j n stratum node nodes step start freq offset conf
+ local i j n stratum node nodes step start freq offset conf options
test_message 1 1 "network with $servers*$server_strata servers and $clients clients:"
print_nondefaults
@@ -411,16 +428,19 @@ run_test() {
start=$server_start
freq=""
[ $i -le $falsetickers ] && offset=$i.0 || offset=0.0
+ options=$server_chronyd_options
elif [ $stratum -le $server_strata ]; then
step=$server_step
start=$server_start
freq=$(get_wander_expr)
offset=0.0
+ options=$server_chronyd_options
else
step=$client_step
start=$client_start
freq=$(get_wander_expr)
offset=$time_offset
+ options=$client_chronyd_options
fi
conf=$(get_chronyd_conf $stratum $i $n)
@@ -431,7 +451,7 @@ run_test() {
echo "node${node}_refclock = $(get_refclock_expr)" >> tmp/conf
echo "node${node}_offset = $offset" >> tmp/conf
echo "node${node}_start = $start" >> tmp/conf
- start_client $node chronyd "$conf" "" "$chronyd_options" && \
+ start_client $node chronyd "$conf" "" "$options" && \
test_ok || test_error
[ $? -ne 0 ] && return 1
diff --git a/test/unit/clientlog.c b/test/unit/clientlog.c
index 515ad1a..a412b69 100644
--- a/test/unit/clientlog.c
+++ b/test/unit/clientlog.c
@@ -65,7 +65,7 @@ test_unit(void)
}
}
- DEBUG_LOG("records %d", ARR_GetSize(records));
+ DEBUG_LOG("records %u", ARR_GetSize(records));
TEST_CHECK(ARR_GetSize(records) == 64);
for (i = j = 0; i < 10000; i++) {
@@ -76,7 +76,7 @@ test_unit(void)
j++;
}
- DEBUG_LOG("requests %u responses %u", i, j);
+ DEBUG_LOG("requests %d responses %d", i, j);
TEST_CHECK(j * 4 < i && j * 6 > i);
CLG_Finalise();
diff --git a/test/unit/hash.c b/test/unit/hash.c
index 8aab74f..5cde039 100644
--- a/test/unit/hash.c
+++ b/test/unit/hash.c
@@ -106,7 +106,7 @@ test_unit(void)
if (j >= tests[i].length)
TEST_CHECK(length == tests[i].length);
else
- TEST_CHECK(length == 0 || length == j);
+ TEST_CHECK(length == j);
TEST_CHECK(!memcmp(out, tests[i].out, length));
}
diff --git a/test/unit/hwclock.c b/test/unit/hwclock.c
index 804e600..216dbfb 100644
--- a/test/unit/hwclock.c
+++ b/test/unit/hwclock.c
@@ -1,6 +1,6 @@
/*
**********************************************************************
- * Copyright (C) Miroslav Lichvar 2016
+ * Copyright (C) Miroslav Lichvar 2016-2017
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of version 2 of the GNU General Public License as
@@ -27,56 +27,58 @@ test_unit(void)
struct timespec start_hw_ts, start_local_ts, hw_ts, local_ts, ts;
HCL_Instance clock;
double freq, jitter, interval, dj, sum;
- int i, j, count;
+ int i, j, k, count;
LCL_Initialise();
- clock = HCL_CreateInstance(1.0);
-
- for (i = 0, count = 0, sum = 0.0; i < 2000; i++) {
- UTI_ZeroTimespec(&start_hw_ts);
- UTI_ZeroTimespec(&start_local_ts);
- UTI_AddDoubleToTimespec(&start_hw_ts, TST_GetRandomDouble(0.0, 1e9), &start_hw_ts);
- UTI_AddDoubleToTimespec(&start_local_ts, TST_GetRandomDouble(0.0, 1e9), &start_local_ts);
-
- DEBUG_LOG("iteration %d", i);
-
- freq = TST_GetRandomDouble(0.9, 1.1);
- jitter = TST_GetRandomDouble(10.0e-9, 1000.0e-9);
- interval = TST_GetRandomDouble(0.1, 10.0);
-
- clock->n_samples = 0;
- clock->valid_coefs = 0;
-
- for (j = 0; j < 100; j++) {
- UTI_AddDoubleToTimespec(&start_hw_ts, j * interval * freq, &hw_ts);
- UTI_AddDoubleToTimespec(&start_local_ts, j * interval, &local_ts);
- if (HCL_CookTime(clock, &hw_ts, &ts, NULL)) {
- dj = fabs(UTI_DiffTimespecsToDouble(&ts, &local_ts) / jitter);
- DEBUG_LOG("delta/jitter %f", dj);
- if (clock->n_samples >= 8)
- sum += dj, count++;
- TEST_CHECK(clock->n_samples < 4 || dj <= 4.0);
- TEST_CHECK(clock->n_samples < 8 || dj <= 3.0);
- }
+ for (i = 1; i <= 8; i++) {
+ clock = HCL_CreateInstance(random() % (1 << i), 1 << i, 1.0);
+
+ for (j = 0, count = 0, sum = 0.0; j < 100; j++) {
+ UTI_ZeroTimespec(&start_hw_ts);
+ UTI_ZeroTimespec(&start_local_ts);
+ UTI_AddDoubleToTimespec(&start_hw_ts, TST_GetRandomDouble(0.0, 1e9), &start_hw_ts);
+ UTI_AddDoubleToTimespec(&start_local_ts, TST_GetRandomDouble(0.0, 1e9), &start_local_ts);
+
+ DEBUG_LOG("iteration %d", j);
+
+ freq = TST_GetRandomDouble(0.9, 1.1);
+ jitter = TST_GetRandomDouble(10.0e-9, 1000.0e-9);
+ interval = TST_GetRandomDouble(0.1, 10.0);
+
+ clock->n_samples = 0;
+ clock->valid_coefs = 0;
- UTI_AddDoubleToTimespec(&start_hw_ts, j * interval * freq + TST_GetRandomDouble(-jitter, jitter), &hw_ts);
+ for (k = 0; k < 100; k++) {
+ UTI_AddDoubleToTimespec(&start_hw_ts, k * interval * freq, &hw_ts);
+ UTI_AddDoubleToTimespec(&start_local_ts, k * interval, &local_ts);
+ if (HCL_CookTime(clock, &hw_ts, &ts, NULL)) {
+ dj = fabs(UTI_DiffTimespecsToDouble(&ts, &local_ts) / jitter);
+ DEBUG_LOG("delta/jitter %f", dj);
+ if (clock->n_samples >= clock->max_samples / 2)
+ sum += dj, count++;
+ TEST_CHECK(clock->n_samples < 4 || dj <= 4.0);
+ TEST_CHECK(clock->n_samples < 8 || dj <= 3.0);
+ }
- if (HCL_NeedsNewSample(clock, &local_ts))
- HCL_AccumulateSample(clock, &hw_ts, &local_ts, 2.0 * jitter);
+ UTI_AddDoubleToTimespec(&start_hw_ts, k * interval * freq + TST_GetRandomDouble(-jitter, jitter), &hw_ts);
- TEST_CHECK(clock->valid_coefs || clock->n_samples < 2);
+ if (HCL_NeedsNewSample(clock, &local_ts))
+ HCL_AccumulateSample(clock, &hw_ts, &local_ts, 2.0 * jitter);
- if (!clock->valid_coefs)
- continue;
+ TEST_CHECK(clock->valid_coefs || clock->n_samples < 2);
- TEST_CHECK(fabs(clock->offset) <= 2.0 * jitter);
+ if (!clock->valid_coefs)
+ continue;
+
+ TEST_CHECK(fabs(clock->offset) <= 2.0 * jitter);
+ }
}
- }
- TEST_CHECK(sum / count < 0.4);
+ TEST_CHECK(sum / count < 2.4 / sqrt(clock->max_samples));
- HCL_DestroyInstance(clock);
+ HCL_DestroyInstance(clock);
+ }
LCL_Finalise();
}
diff --git a/test/unit/ntp_core.c b/test/unit/ntp_core.c
index 9587306..5e519e5 100644
--- a/test/unit/ntp_core.c
+++ b/test/unit/ntp_core.c
@@ -1,6 +1,6 @@
/*
**********************************************************************
- * Copyright (C) Miroslav Lichvar 2017
+ * Copyright (C) Miroslav Lichvar 2017-2018
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of version 2 of the GNU General Public License as
@@ -63,6 +63,18 @@ advance_time(double x)
UTI_AddDoubleToTimespec(&current_time, x, &current_time);
}
+static uint32_t
+get_random_key_id(void)
+{
+ uint32_t id;
+
+ do {
+ id = random() % 6 + 2;
+ } while (!KEY_KeyKnown(id));
+
+ return id;
+}
+
static void
send_request(NCR_Instance inst)
{
@@ -122,6 +134,7 @@ static void
send_response(int interleaved, int authenticated, int allow_update, int valid_ts, int valid_auth)
{
NTP_Packet *req, *res;
+ int auth_len = 0;
req = &req_buffer.ntp_pkt;
res = &res_buffer.ntp_pkt;
@@ -168,24 +181,41 @@ send_response(int interleaved, int authenticated, int allow_update, int valid_ts
}
if (authenticated) {
- res->auth_keyid = req->auth_keyid;
- KEY_GenerateAuth(ntohl(res->auth_keyid), (unsigned char *)res, NTP_NORMAL_PACKET_LENGTH,
- res->auth_data, 16);
- res_length = NTP_NORMAL_PACKET_LENGTH + 4 + 16;
+ res->auth_keyid = req->auth_keyid ? req->auth_keyid : htonl(get_random_key_id());
+ auth_len = KEY_GetAuthLength(ntohl(res->auth_keyid));
+ assert(auth_len);
+ if (NTP_LVM_TO_VERSION(res->lvm) == 4 && random() % 2)
+ auth_len = MIN(auth_len, NTP_MAX_V4_MAC_LENGTH - 4);
+
+ if (KEY_GenerateAuth(ntohl(res->auth_keyid), (unsigned char *)res,
+ NTP_NORMAL_PACKET_LENGTH, res->auth_data, auth_len) != auth_len)
+ assert(0);
+ res_length = NTP_NORMAL_PACKET_LENGTH + 4 + auth_len;
} else {
res_length = NTP_NORMAL_PACKET_LENGTH;
}
- if (!valid_auth) {
- switch (random() % 3) {
+ if (!valid_auth && authenticated) {
+ assert(auth_len);
+
+ switch (random() % 4) {
case 0:
- res->auth_keyid++;
+ res->auth_keyid = htonl(ntohl(res->auth_keyid) + 1);
break;
case 1:
- res->auth_data[random() % 16]++;
+ res->auth_keyid = htonl(ntohl(res->auth_keyid) ^ 1);
+ if (KEY_GenerateAuth(ntohl(res->auth_keyid), (unsigned char *)res,
+ NTP_NORMAL_PACKET_LENGTH, res->auth_data, auth_len) != auth_len)
+ assert(0);
break;
case 2:
- res_length = NTP_NORMAL_PACKET_LENGTH;
+ res->auth_data[random() % auth_len]++;
+ break;
+ case 3:
+ res_length = NTP_NORMAL_PACKET_LENGTH + 4 * (random() % ((4 + auth_len) / 4));
+ if (NTP_LVM_TO_VERSION(res->lvm) == 4 &&
+ res_length == NTP_NORMAL_PACKET_LENGTH + NTP_MAX_V4_MAC_LENGTH)
+ res_length -= 4;
break;
default:
assert(0);
@@ -292,7 +322,10 @@ test_unit(void)
NIO_Initialise(IPADDR_UNSPEC);
NCR_Initialise();
REF_Initialise();
+
+ TST_SuspendLogging();
KEY_Initialise();
+ TST_ResumeLogging();
CNF_SetupAccessRestrictions();
@@ -302,7 +335,7 @@ test_unit(void)
if (random() % 2)
source.params.interleaved = 1;
if (random() % 2)
- source.params.authkey = 1;
+ source.params.authkey = get_random_key_id();
source.params.version = random() % 4 + 1;
UTI_ZeroTimespec(&current_time);
diff --git a/test/unit/ntp_core.keys b/test/unit/ntp_core.keys
index 7a70e52..f06237f 100644
--- a/test/unit/ntp_core.keys
+++ b/test/unit/ntp_core.keys
@@ -1,2 +1,6 @@
-1 MD5 HEX:38979C567358C0896F4D9D459A3C8B8478654579
2 MD5 HEX:38979C567358C0896F4D9D459A3C8B8478654579
+3 MD5 HEX:38979C567358C0896F4D9D459A3C8B8478654579
+4 SHA1 HEX:B71744EA01FBF01CA30D173ECDDF901952AE356A
+5 SHA1 HEX:B71744EA01FBF01CA30D173ECDDF901952AE356A
+6 SHA512 HEX:DE027482F22B201FC20863F58C74095E7906089F
+7 SHA512 HEX:DE027482F22B201FC20863F58C74095E7906089F
diff --git a/test/unit/samplefilt.c b/test/unit/samplefilt.c
new file mode 100644
index 0000000..294a9bf
--- /dev/null
+++ b/test/unit/samplefilt.c
@@ -0,0 +1,113 @@
+/*
+ **********************************************************************
+ * Copyright (C) Miroslav Lichvar 2018
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of version 2 of the GNU General Public License as
+ * published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ **********************************************************************
+ */
+
+#include <samplefilt.c>
+#include "test.h"
+
+void
+test_unit(void)
+{
+ NTP_Sample sample_in, sample_out;
+ SPF_Instance filter;
+ int i, j, k, sum_count, min_samples, max_samples;
+ double mean, combine_ratio, sum_err;
+
+ LCL_Initialise();
+
+ for (i = 0; i <= 100; i++) {
+ max_samples = random() % 20 + 1;
+ min_samples = random() % (max_samples) + 1;
+ combine_ratio = TST_GetRandomDouble(0.0, 1.0);
+
+ filter = SPF_CreateInstance(min_samples, max_samples, 2.0, combine_ratio);
+
+ for (j = 0, sum_count = 0, sum_err = 0.0; j < 100; j++) {
+ DEBUG_LOG("iteration %d/%d", i, j);
+
+ mean = TST_GetRandomDouble(-1.0e3, 1.0e3);
+ UTI_ZeroTimespec(&sample_in.time);
+
+ for (k = 0; k < 100; k++) {
+ UTI_AddDoubleToTimespec(&sample_in.time, TST_GetRandomDouble(1.0e-1, 1.0e2),
+ &sample_in.time);
+ sample_in.offset = mean + TST_GetRandomDouble(-1.0, 1.0);
+ sample_in.peer_dispersion = TST_GetRandomDouble(1.0e-4, 2.0e-4);
+ sample_in.root_dispersion = TST_GetRandomDouble(1.0e-3, 2.0e-3);
+ sample_in.peer_delay = TST_GetRandomDouble(1.0e-2, 2.0e-2);
+ sample_in.root_delay = TST_GetRandomDouble(1.0e-1, 2.0e-1);
+ sample_in.stratum = random() % 16;
+ sample_in.leap = random() % 4;
+
+ TEST_CHECK(SPF_AccumulateSample(filter, &sample_in));
+ TEST_CHECK(!SPF_AccumulateSample(filter, &sample_in));
+
+ TEST_CHECK(SPF_GetNumberOfSamples(filter) == MIN(k + 1, max_samples));
+
+ SPF_GetLastSample(filter, &sample_out);
+ TEST_CHECK(!memcmp(&sample_in, &sample_out, sizeof (sample_in)));
+
+ SPF_SlewSamples(filter, &sample_in.time, 0.0, 0.0);
+ SPF_AddDispersion(filter, 0.0);
+
+ if (k + 1 < min_samples)
+ TEST_CHECK(!SPF_GetFilteredSample(filter, &sample_out));
+
+ TEST_CHECK(SPF_GetNumberOfSamples(filter) == MIN(k + 1, max_samples));
+ }
+
+ if (random() % 10) {
+ TEST_CHECK(SPF_GetFilteredSample(filter, &sample_out));
+
+ TEST_CHECK(SPF_GetAvgSampleDispersion(filter) <= 2.0);
+
+ sum_err += sample_out.offset - mean;
+ sum_count++;
+
+ TEST_CHECK(UTI_CompareTimespecs(&sample_out.time, &sample_in.time) <= 0 &&
+ sample_out.time.tv_sec >= 0);
+ TEST_CHECK(fabs(sample_out.offset - mean) <= 1.0);
+ TEST_CHECK(sample_out.peer_dispersion >= 1.0e-4 &&
+ (sample_out.peer_dispersion <= 2.0e-4 || filter->max_samples > 1));
+ TEST_CHECK(sample_out.root_dispersion >= 1.0e-3 &&
+ (sample_out.root_dispersion <= 2.0e-3 || filter->max_samples > 1));
+ TEST_CHECK(sample_out.peer_delay >= 1.0e-2 &&
+ sample_out.peer_delay <= 2.0e-2);
+ TEST_CHECK(sample_out.root_delay >= 1.0e-1 &&
+ sample_out.root_delay <= 2.0e-1);
+ TEST_CHECK(sample_out.leap >= 0 && sample_out.leap <= 3);
+ TEST_CHECK(sample_out.stratum >= 0 && sample_out.stratum <= 15);
+
+ if (max_samples == 1)
+ TEST_CHECK(!memcmp(&sample_in, &sample_out, sizeof (sample_in)));
+
+ } else {
+ SPF_DropSamples(filter);
+ }
+
+ TEST_CHECK(SPF_GetNumberOfSamples(filter) == 0);
+ }
+
+ TEST_CHECK(fabs(sum_err / sum_count) < 0.3);
+
+ SPF_DestroyInstance(filter);
+ }
+
+ LCL_Finalise();
+}
diff --git a/test/unit/sources.c b/test/unit/sources.c
index 341e22e..b81f808 100644
--- a/test/unit/sources.c
+++ b/test/unit/sources.c
@@ -26,10 +26,9 @@ test_unit(void)
{
SRC_Instance srcs[16];
RPT_SourceReport report;
+ NTP_Sample sample;
IPAddr addr;
int i, j, k, l, samples, sel_options;
- double offset, delay, disp;
- struct timespec ts;
CNF_Initialise(0, 0);
LCL_Initialise();
@@ -59,21 +58,25 @@ test_unit(void)
samples = (i + j) % 5 + 3;
- offset = TST_GetRandomDouble(-1.0, 1.0);
+ sample.offset = TST_GetRandomDouble(-1.0, 1.0);
for (k = 0; k < samples; k++) {
- SCH_GetLastEventTime(&ts, NULL, NULL);
- UTI_AddDoubleToTimespec(&ts, TST_GetRandomDouble(k - samples, k - samples + 1), &ts);
-
- offset += TST_GetRandomDouble(-1.0e-2, 1.0e-2);
- delay = TST_GetRandomDouble(1.0e-6, 1.0e-1);
- disp = TST_GetRandomDouble(1.0e-6, 1.0e-1);
+ SCH_GetLastEventTime(&sample.time, NULL, NULL);
+ UTI_AddDoubleToTimespec(&sample.time, TST_GetRandomDouble(k - samples, k - samples + 1),
+ &sample.time);
+
+ sample.offset += TST_GetRandomDouble(-1.0e-2, 1.0e-2);
+ sample.peer_delay = TST_GetRandomDouble(1.0e-6, 1.0e-1);
+ sample.peer_dispersion = TST_GetRandomDouble(1.0e-6, 1.0e-1);
+ sample.root_delay = sample.peer_delay;
+ sample.root_dispersion = sample.peer_dispersion;
+ sample.stratum = 1;
+ sample.leap = LEAP_Normal;
DEBUG_LOG("source %d sample %d offset %f delay %f disp %f", j, k,
- offset, delay, disp);
+ sample.offset, sample.peer_delay, sample.peer_dispersion);
- SRC_AccumulateSample(srcs[j], &ts, offset, delay, disp, delay, disp,
- 1, LEAP_Normal);
+ SRC_AccumulateSample(srcs[j], &sample);
}
for (k = 0; k <= j; k++) {
@@ -82,7 +85,7 @@ test_unit(void)
double passed_lo = DBL_MAX, passed_hi = DBL_MIN;
SRC_SelectSource(srcs[k]);
- DEBUG_LOG("source %d status %d", k, sources[k]->status);
+ DEBUG_LOG("source %d status %u", k, sources[k]->status);
for (l = 0; l <= j; l++) {
TEST_CHECK(sources[l]->status > SRC_OK && sources[l]->status <= SRC_SELECTED);
@@ -125,7 +128,7 @@ test_unit(void)
}
for (j = 0; j < sizeof (srcs) / sizeof (srcs[0]); j++) {
- SRC_ReportSource(j, &report, &ts);
+ SRC_ReportSource(j, &report, &sample.time);
SRC_DestroyInstance(srcs[j]);
}
}
diff --git a/test/unit/test.c b/test/unit/test.c
index 67f7678..3a9ec74 100644
--- a/test/unit/test.c
+++ b/test/unit/test.c
@@ -75,6 +75,16 @@ main(int argc, char **argv)
return 0;
}
+void TST_SuspendLogging(void)
+{
+ LOG_OpenFileLog("/dev/null");
+}
+
+void TST_ResumeLogging(void)
+{
+ LOG_OpenFileLog(NULL);
+}
+
double
TST_GetRandomDouble(double min, double max)
{
diff --git a/test/unit/test.h b/test/unit/test.h
index d96f3af..f409252 100644
--- a/test/unit/test.h
+++ b/test/unit/test.h
@@ -35,6 +35,9 @@ extern void test_unit(void);
extern void TST_Fail(int line);
+extern void TST_SuspendLogging(void);
+extern void TST_ResumeLogging(void);
+
extern double TST_GetRandomDouble(double min, double max);
extern void TST_GetRandomAddress(IPAddr *ip, int family, int bits);
extern void TST_SwapAddressBit(IPAddr *ip, unsigned int b);
diff --git a/test/unit/util.c b/test/unit/util.c
index 5f1a653..6ce6f90 100644
--- a/test/unit/util.c
+++ b/test/unit/util.c
@@ -3,13 +3,17 @@
void test_unit(void) {
NTP_int64 ntp_ts, ntp_fuzz;
+ NTP_int32 ntp32_ts;
struct timespec ts, ts2;
struct timeval tv;
struct sockaddr_un sun;
- double x, y;
+ double x, y, nan, inf;
+ Timespec tspec;
Float f;
int i, j, c;
char buf[16], *s;
+ uid_t uid;
+ gid_t gid;
for (i = -31; i < 31; i++) {
x = pow(2.0, i);
@@ -33,6 +37,11 @@ void test_unit(void) {
TEST_CHECK(x > 0.0 || x <= 0.0);
}
+ for (i = 0; i < 100000; i++) {
+ UTI_GetRandomBytes(&ntp32_ts, sizeof (ntp32_ts));
+ TEST_CHECK(UTI_DoubleToNtp32(UTI_Ntp32ToDouble(ntp32_ts)) == ntp32_ts);
+ }
+
TEST_CHECK(UTI_DoubleToNtp32(1.0) == htonl(65536));
TEST_CHECK(UTI_DoubleToNtp32(0.0) == htonl(0));
TEST_CHECK(UTI_DoubleToNtp32(1.0 / (65536.0)) == htonl(1));
@@ -175,6 +184,23 @@ void test_unit(void) {
TEST_CHECK(c > 400 && c < 600);
}
+ ts.tv_nsec = 0;
+
+ ts.tv_sec = 10;
+ TEST_CHECK(!UTI_IsTimeOffsetSane(&ts, -20.0));
+
+#ifdef HAVE_LONG_TIME_T
+ ts.tv_sec = NTP_ERA_SPLIT + (1LL << 32);
+#else
+ ts.tv_sec = 0x7fffffff - MIN_ENDOFTIME_DISTANCE;
+#endif
+ TEST_CHECK(!UTI_IsTimeOffsetSane(&ts, 10.0));
+ TEST_CHECK(UTI_IsTimeOffsetSane(&ts, -20.0));
+
+ UTI_TimespecHostToNetwork(&ts, &tspec);
+ UTI_TimespecNetworkToHost(&tspec, &ts2);
+ TEST_CHECK(!UTI_CompareTimespecs(&ts, &ts2));
+
for (i = c = 0; i < 100000; i++) {
j = random() % (sizeof (buf) + 1);
UTI_GetRandomBytes(buf, j);
@@ -196,4 +222,46 @@ void test_unit(void) {
TEST_CHECK(s[BUFFER_LENGTH - 2] == '>');
}
}
+
+ s = UTI_PathToDir("/aaa/bbb/ccc/ddd");
+ TEST_CHECK(!strcmp(s, "/aaa/bbb/ccc"));
+ Free(s);
+ s = UTI_PathToDir("aaa");
+ TEST_CHECK(!strcmp(s, "."));
+ Free(s);
+ s = UTI_PathToDir("/aaaa");
+ TEST_CHECK(!strcmp(s, "/"));
+ Free(s);
+
+ nan = strtod("nan", NULL);
+ inf = strtod("inf", NULL);
+
+ TEST_CHECK(MIN(2.0, -1.0) == -1.0);
+ TEST_CHECK(MIN(-1.0, 2.0) == -1.0);
+ TEST_CHECK(MIN(inf, 2.0) == 2.0);
+
+ TEST_CHECK(MAX(2.0, -1.0) == 2.0);
+ TEST_CHECK(MAX(-1.0, 2.0) == 2.0);
+ TEST_CHECK(MAX(inf, 2.0) == inf);
+
+ TEST_CHECK(CLAMP(1.0, -1.0, 2.0) == 1.0);
+ TEST_CHECK(CLAMP(1.0, 3.0, 2.0) == 2.0);
+ TEST_CHECK(CLAMP(1.0, inf, 2.0) == 2.0);
+ TEST_CHECK(CLAMP(1.0, nan, 2.0) == 2.0);
+
+ TEST_CHECK(SQUARE(3.0) == 3.0 * 3.0);
+
+ rmdir("testdir");
+
+ uid = geteuid();
+ gid = getegid();
+
+ TEST_CHECK(UTI_CreateDirAndParents("testdir", 0700, uid, gid));
+
+ TST_SuspendLogging();
+ TEST_CHECK(UTI_CheckDirPermissions("testdir", 0700, uid, gid));
+ TEST_CHECK(!UTI_CheckDirPermissions("testdir", 0300, uid, gid));
+ TEST_CHECK(!UTI_CheckDirPermissions("testdir", 0700, uid + 1, gid));
+ TEST_CHECK(!UTI_CheckDirPermissions("testdir", 0700, uid, gid + 1));
+ TST_ResumeLogging();
}