Improve timeout control in routing tests

This commit is contained in:
Andrew Bettison 2013-04-22 16:01:38 +09:30
parent e66c39a213
commit 121ae2d609
6 changed files with 103 additions and 46 deletions

5
cli.c
View File

@ -360,6 +360,11 @@ int cli_uint(const char *arg)
return s != arg && *s == '\0'; return s != arg && *s == '\0';
} }
int cli_interval_ms(const char *arg)
{
return str_to_uint64_interval_ms(arg, NULL, NULL);
}
int cli_optional_did(const char *text) int cli_optional_did(const char *text)
{ {
return text[0] == '\0' || str_is_did(text); return text[0] == '\0' || str_is_did(text);

1
cli.h
View File

@ -69,6 +69,7 @@ int cli_optional_bundle_key(const char *arg);
int cli_manifestid(const char *arg); int cli_manifestid(const char *arg);
int cli_fileid(const char *arg); int cli_fileid(const char *arg);
int cli_optional_bundle_crypt_key(const char *arg); int cli_optional_bundle_crypt_key(const char *arg);
int cli_interval_ms(const char *arg);
int cli_uint(const char *arg); int cli_uint(const char *arg);
int cli_optional_did(const char *text); int cli_optional_did(const char *text);

View File

@ -936,15 +936,17 @@ int app_mdp_ping(const struct cli_parsed *parsed, void *context)
{ {
if (config.debug.verbose) if (config.debug.verbose)
DEBUG_cli_parsed(parsed); DEBUG_cli_parsed(parsed);
const char *sidhex, *count; const char *sidhex, *count, *opt_timeout;
if (cli_arg(parsed, "SID", &sidhex, str_is_subscriber_id, "broadcast") == -1) if ( cli_arg(parsed, "--timeout", &opt_timeout, cli_interval_ms, "1") == -1
return -1; || cli_arg(parsed, "SID", &sidhex, str_is_subscriber_id, "broadcast") == -1
if (cli_arg(parsed, "count", &count, NULL, "0") == -1) || cli_arg(parsed, "count", &count, cli_uint, "0") == -1)
return -1; return -1;
// assume we wont hear any responses // assume we wont hear any responses
int ret=1; int ret=1;
int icount=atoi(count); int icount=atoi(count);
time_ms_t timeout_ms = 1000;
str_to_uint64_interval_ms(opt_timeout, &timeout_ms, NULL);
overlay_mdp_frame mdp; overlay_mdp_frame mdp;
bzero(&mdp, sizeof(overlay_mdp_frame)); bzero(&mdp, sizeof(overlay_mdp_frame));
@ -977,8 +979,8 @@ int app_mdp_ping(const struct cli_parsed *parsed, void *context)
long long rx_count=0,tx_count=0; long long rx_count=0,tx_count=0;
if (broadcast) if (broadcast)
WHY("WARNING: broadcast ping packets will not be encryped."); WARN("broadcast ping packets will not be encrypted");
while(icount==0 || tx_count<icount) { for (; icount==0 || tx_count<icount; ++sequence_number) {
/* Now send the ping packets */ /* Now send the ping packets */
mdp.packetTypeAndFlags=MDP_TX; mdp.packetTypeAndFlags=MDP_TX;
if (broadcast) mdp.packetTypeAndFlags|=MDP_NOCRYPT; if (broadcast) mdp.packetTypeAndFlags|=MDP_NOCRYPT;
@ -995,18 +997,21 @@ int app_mdp_ping(const struct cli_parsed *parsed, void *context)
int res=overlay_mdp_send(&mdp,0,0); int res=overlay_mdp_send(&mdp,0,0);
if (res) { if (res) {
WHYF("ERROR: Could not dispatch PING frame #%d (error %d)", sequence_number - firstSeq, res); WHYF("could not dispatch PING frame #%d (error %d)%s%s",
if (mdp.packetTypeAndFlags==MDP_ERROR) sequence_number - firstSeq,
WHYF(" Error message: %s", mdp.error.message); res,
} else tx_count++; mdp.packetTypeAndFlags == MDP_ERROR ? ": " : "",
mdp.packetTypeAndFlags == MDP_ERROR ? mdp.error.message : ""
);
} else
tx_count++;
/* Now look for replies until one second has passed, and print any replies /* Now look for replies until one second has passed, and print any replies
with appropriate information as required */ with appropriate information as required */
time_ms_t now = gettime_ms(); time_ms_t now = gettime_ms();
time_ms_t timeout = now + 1000; time_ms_t finish = now + timeout_ms;
for (; !servalShutdown && (timeout_ms == 0 || now < finish); now = gettime_ms()) {
while(now<timeout) { time_ms_t timeout_ms = finish - gettime_ms();
time_ms_t timeout_ms = timeout - gettime_ms();
int result = overlay_mdp_client_poll(timeout_ms); int result = overlay_mdp_client_poll(timeout_ms);
if (result>0) { if (result>0) {
@ -1045,12 +1050,7 @@ int app_mdp_ping(const struct cli_parsed *parsed, void *context)
} }
} }
} }
now=gettime_ms();
if (servalShutdown)
break;
} }
sequence_number++;
timeout=now+1000;
} }
{ {
@ -1421,12 +1421,25 @@ int app_rhizome_add_file(const struct cli_parsed *parsed, void *context)
int app_slip_test(const struct cli_parsed *parsed, void *context) int app_slip_test(const struct cli_parsed *parsed, void *context)
{ {
int len; const char *seed = NULL;
unsigned char bufin[8192]; const char *iterations = NULL;
unsigned char bufout[8192]; const char *duration = NULL;
int count=0; if ( cli_arg(parsed, "--seed", &seed, cli_uint, NULL) == -1
for(count=0;count<50000;count++) { || cli_arg(parsed, "--duration", &duration, cli_uint, NULL) == -1
len=1+random()%1500; || cli_arg(parsed, "--iterations", &iterations, cli_uint, NULL) == -1)
return -1;
if (seed)
srandom(atoi(seed));
int maxcount = iterations ? atoi(iterations) : duration ? 0 : 1000;
time_ms_t start = duration ? gettime_ms() : 0;
time_ms_t end = duration ? start + atoi(duration) * (time_ms_t) 1000 : 0;
int count;
for (count = 0; maxcount == 0 || count < maxcount; ++count) {
if (end && gettime_ms() >= end)
break;
unsigned char bufin[8192];
unsigned char bufout[8192];
int len=1+random()%1500;
int i; int i;
for(i=0;i<len;i++) bufin[i]=random()&0xff; for(i=0;i<len;i++) bufin[i]=random()&0xff;
struct slip_decode_state state; struct slip_decode_state state;
@ -1439,11 +1452,10 @@ int app_slip_test(const struct cli_parsed *parsed, void *context)
dump("input",bufin,len); dump("input",bufin,len);
dump("encoded",bufout,outlen); dump("encoded",bufout,outlen);
dump("decoded",state.dst,state.packet_length); dump("decoded",state.dst,state.packet_length);
exit(-1); return 1;
} else { } else {
if (!(count%1000)) { if (!(count%1000))
printf("."); fflush(stdout); printf("."); fflush(stdout);
}
} }
} }
printf("Test passed.\n"); printf("Test passed.\n");
@ -2352,7 +2364,7 @@ struct cli_schema command_line_options[]={
"Stop a running daemon with instance path from SERVALINSTANCE_PATH environment variable."}, "Stop a running daemon with instance path from SERVALINSTANCE_PATH environment variable."},
{app_server_status,{"status",NULL},CLIFLAG_PERMISSIVE_CONFIG, {app_server_status,{"status",NULL},CLIFLAG_PERMISSIVE_CONFIG,
"Display information about running daemon."}, "Display information about running daemon."},
{app_mdp_ping,{"mdp","ping","<SID>|broadcast","[<count>]",NULL}, 0, {app_mdp_ping,{"mdp","ping","[--timeout=<seconds>]","<SID>|broadcast","[<count>]",NULL}, 0,
"Attempts to ping specified node via Mesh Datagram Protocol (MDP)."}, "Attempts to ping specified node via Mesh Datagram Protocol (MDP)."},
{app_trace,{"mdp","trace","<SID>",NULL}, 0, {app_trace,{"mdp","trace","<SID>",NULL}, 0,
"Trace through the network to the specified node via MDP."}, "Trace through the network to the specified node via MDP."},
@ -2431,7 +2443,7 @@ struct cli_schema command_line_options[]={
"Interactive servald monitor interface."}, "Interactive servald monitor interface."},
{app_crypt_test,{"test","crypt",NULL}, 0, {app_crypt_test,{"test","crypt",NULL}, 0,
"Run cryptography speed test"}, "Run cryptography speed test"},
{app_slip_test,{"test","slip",NULL}, 0, {app_slip_test,{"test","slip","[--seed=<N>]","[--duration=<seconds>|--iterations=<N>]",NULL}, 0,
"Run serial encapsulation test"}, "Run serial encapsulation test"},
#ifdef HAVE_VOIPTEST #ifdef HAVE_VOIPTEST
{app_pa_phone,{"phone",NULL}, 0, {app_pa_phone,{"phone",NULL}, 0,

30
str.c
View File

@ -236,7 +236,8 @@ int str_to_int64_scaled(const char *str, int base, int64_t *result, const char *
*afterp = end; *afterp = end;
else if (*end) else if (*end)
return 0; return 0;
*result = value; if (result)
*result = value;
return 1; return 1;
} }
@ -253,7 +254,8 @@ int str_to_uint64_scaled(const char *str, int base, uint64_t *result, const char
*afterp = end; *afterp = end;
else if (*end) else if (*end)
return 0; return 0;
*result = value; if (result)
*result = value;
return 1; return 1;
} }
@ -274,6 +276,30 @@ int uint64_scaled_to_str(char *str, size_t len, uint64_t value)
return strbuf_overrun(b) ? 0 : 1; return strbuf_overrun(b) ? 0 : 1;
} }
int str_to_uint64_interval_ms(const char *str, int64_t *result, const char **afterp)
{
const unsigned precision = 1000;
if (isspace(*str))
return 0;
const char *end = str;
unsigned long long value = strtoull(str, (char**)&end, 10) * precision;
if (end == str)
return 0;
if (end[0] == '.' && isdigit(end[1])) {
++end;
unsigned factor;
for (factor = precision / 10; isdigit(*end) && factor; factor /= 10)
value += (*end++ - '0') * factor;
}
if (afterp)
*afterp = end;
else if (*end)
return 0;
if (result)
*result = value;
return 1;
}
/* Format a buffer of data as a printable representation, eg: "Abc\x0b\n\0", for display /* Format a buffer of data as a printable representation, eg: "Abc\x0b\n\0", for display
in log messages. in log messages.
@author Andrew Bettison <andrew@servalproject.com> @author Andrew Bettison <andrew@servalproject.com>

13
str.h
View File

@ -207,6 +207,19 @@ uint64_t scale_factor(const char *str, const char **afterp);
*/ */
int uint64_scaled_to_str(char *str, size_t len, uint64_t value); int uint64_scaled_to_str(char *str, size_t len, uint64_t value);
/* Parse a string as a time interval (seconds) in millisecond resolution. Return the number of
* milliseconds. Valid strings are all unsigned ASCII decimal numbers with up to three digits after
* the decimal point.
*
* Return 1 if a valid interval was parsed, storing the number of milliseconds in *result (unless
* result is NULL) and storing a pointer to the immediately succeeding character in *afterp (unless
* afterp is NULL, in which case returns 1 only if the immediately succeeding character is a nul
* '\0'). Returns 0 otherwise, leaving *result and *afterp unchanged.
*
* @author Andrew Bettison <andrew@servalproject.com>
*/
int str_to_uint64_interval_ms(const char *str, int64_t *result, const char **afterp);
/* Return true if the string resembles a nul-terminated URI. /* Return true if the string resembles a nul-terminated URI.
* Based on RFC-3986 generic syntax, assuming nothing about the hierarchical part. * Based on RFC-3986 generic syntax, assuming nothing about the hierarchical part.
* *

View File

@ -74,7 +74,7 @@ test_single_link() {
foreach_instance +A +B \ foreach_instance +A +B \
wait_until has_seen_instances +A +B wait_until has_seen_instances +A +B
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDB 1 executeOk_servald mdp ping --timeout=15 $SIDB 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :" assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :"
@ -92,13 +92,13 @@ test_multiple_ids() {
foreach_instance +A +B \ foreach_instance +A +B \
wait_until has_seen_instances +A +B wait_until has_seen_instances +A +B
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDB2 1 executeOk_servald mdp ping --timeout=15 $SIDB2 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB1:BROADCAST UNICAST :dummy.*:0*" assertStdoutGrep --matches=1 "^$SIDB1:BROADCAST UNICAST :dummy.*:0*"
assertStdoutGrep --matches=1 "^$SIDB2:INDIRECT ::$SIDB1" assertStdoutGrep --matches=1 "^$SIDB2:INDIRECT ::$SIDB1"
set_instance +B set_instance +B
executeOk_servald mdp ping $SIDA2 1 executeOk_servald mdp ping --timeout=15 $SIDA2 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDA1:BROADCAST UNICAST :dummy.*:0*" assertStdoutGrep --matches=1 "^$SIDA1:BROADCAST UNICAST :dummy.*:0*"
@ -118,7 +118,7 @@ test_single_mdp() {
foreach_instance +A +B \ foreach_instance +A +B \
wait_until has_seen_instances +A +B wait_until has_seen_instances +A +B
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDB 1 executeOk_servald mdp ping --timeout=15 $SIDB 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :" assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :"
@ -137,7 +137,7 @@ test_mismatched_encap() {
foreach_instance +A +B \ foreach_instance +A +B \
wait_until has_seen_instances +A +B wait_until has_seen_instances +A +B
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDB 1 executeOk_servald mdp ping --timeout=15 $SIDB 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :" assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :"
@ -149,7 +149,7 @@ setup_slip_encoding() {
assert_no_servald_processes assert_no_servald_processes
} }
test_slip_encoding() { test_slip_encoding() {
executeOk_servald test slip executeOk_servald test slip --seed=1 --iterations=2000
} }
doc_multiple_nodes="Multiple nodes on one link" doc_multiple_nodes="Multiple nodes on one link"
@ -164,11 +164,11 @@ test_multiple_nodes() {
foreach +A +B +C +D \ foreach +A +B +C +D \
wait_until has_seen_instances +A +B +C +D wait_until has_seen_instances +A +B +C +D
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDB 1 executeOk_servald mdp ping --timeout=15 $SIDB 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald mdp ping $SIDC 1 executeOk_servald mdp ping --timeout=15 $SIDC 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald mdp ping $SIDD 1 executeOk_servald mdp ping --timeout=15 $SIDD 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB:BROADCAST " assertStdoutGrep --matches=1 "^$SIDB:BROADCAST "
@ -195,7 +195,7 @@ test_scan() {
executeOk_servald scan executeOk_servald scan
wait_until scan_completed wait_until scan_completed
wait_until has_seen_instances +B wait_until has_seen_instances +B
executeOk_servald mdp ping $SIDB 1 executeOk_servald mdp ping --timeout=15 $SIDB 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB:UNICAST :" assertStdoutGrep --matches=1 "^$SIDB:UNICAST :"
@ -220,7 +220,7 @@ test_broadcast_only() {
foreach_instance +A +B \ foreach_instance +A +B \
wait_until has_seen_instances +A +B wait_until has_seen_instances +A +B
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDB 1 executeOk_servald mdp ping --timeout=15 $SIDB 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB:BROADCAST :" assertStdoutGrep --matches=1 "^$SIDB:BROADCAST :"
@ -242,7 +242,7 @@ test_prefer_unicast() {
foreach_instance +A +B \ foreach_instance +A +B \
wait_until has_seen_instances +A +B wait_until has_seen_instances +A +B
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDB 1 executeOk_servald mdp ping --timeout=15 $SIDB 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :" assertStdoutGrep --matches=1 "^$SIDB:BROADCAST UNICAST :"
@ -263,7 +263,7 @@ test_multihop_linear() {
foreach_instance +A +B +C +D \ foreach_instance +A +B +C +D \
wait_until has_seen_instances +A +B +C +D wait_until has_seen_instances +A +B +C +D
set_instance +A set_instance +A
executeOk_servald --stdout --stderr mdp ping $SIDD 1 executeOk_servald --stdout --stderr mdp ping --timeout=15 $SIDD 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald mdp trace $SIDD executeOk_servald mdp trace $SIDD
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
@ -293,7 +293,7 @@ test_crowded_mess() {
foreach_instance +A +H \ foreach_instance +A +H \
wait_until has_seen_instances +A +H wait_until has_seen_instances +A +H
set_instance +A set_instance +A
executeOk_servald mdp ping $SIDH 1 executeOk_servald mdp ping --timeout=15 $SIDH 1
tfw_cat --stdout --stderr tfw_cat --stdout --stderr
executeOk_servald route print executeOk_servald route print
assertStdoutGrep --matches=1 "^$SIDH:INDIRECT :" assertStdoutGrep --matches=1 "^$SIDH:INDIRECT :"