mirror of https://github.com/getdnsapi/getdns.git
Fix fallback failures. Add manual regression test script.
This commit is contained in:
parent
3cbef7ee9e
commit
ab60211020
|
@ -0,0 +1,120 @@
|
||||||
|
#!/usr/bin/env bash
|
||||||
|
|
||||||
|
DIR=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )
|
||||||
|
SERVER_IP="8.8.8.8"
|
||||||
|
TLS_SERVER_IP="185.49.141.38"
|
||||||
|
GOOD_RESULT_SYNC="Status was: At least one response was returned"
|
||||||
|
GOOD_RESULT_ASYNC="successfull"
|
||||||
|
BAD_RESULT_SYNC="1 'Generic error'"
|
||||||
|
BAD_RESULT_ASYNC="callback_type of 703"
|
||||||
|
GOOD_COUNT=0
|
||||||
|
FAIL_COUNT=0
|
||||||
|
|
||||||
|
check_good () {
|
||||||
|
result=`echo $1 | grep "Response code was: GOOD." | tail -1 | sed 's/ All done.'// | sed 's/Response code was: GOOD. '//`
|
||||||
|
async_success=`echo $result | grep -c "$GOOD_RESULT_ASYNC"`
|
||||||
|
if [[ $result =~ $GOOD_RESULT_SYNC ]] || [[ $async_success =~ 1 ]]; then
|
||||||
|
(( GOOD_COUNT++ ))
|
||||||
|
echo -n "PASS: "
|
||||||
|
else
|
||||||
|
(( FAIL_COUNT++ ))
|
||||||
|
echo "FAIL (RESULT): " $1
|
||||||
|
echo -n "FAIL: "
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
check_bad () {
|
||||||
|
result=`echo $1 | grep "An error occurred:" | tail -1 | sed 's/ All done.'//`
|
||||||
|
error=` echo $result | sed 's/An error occurred: //'`
|
||||||
|
if [[ ! -z $result ]]; then
|
||||||
|
if [[ $error =~ $BAD_RESULT_SYNC ]] || [[ $error =~ $BAD_RESULT_ASYNC ]]; then
|
||||||
|
(( GOOD_COUNT++ ))
|
||||||
|
echo -n "PASS:"
|
||||||
|
else
|
||||||
|
(( FAIL_COUNT++ ))
|
||||||
|
echo "FAIL (RESULT): " $error
|
||||||
|
echo -n "FAIL: "
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
(( FAIL_COUNT++ ))
|
||||||
|
echo "FAIL (RESULT): " $1
|
||||||
|
echo -n "FAIL: "
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
usage () {
|
||||||
|
echo "This is a basic and temporary testing script for the transport list"
|
||||||
|
echo "functionality that utilises getdns_query to perform multiple queries."
|
||||||
|
echo "It will be replaced by an automated test harness in future, but"
|
||||||
|
echo "it can be used to check the basic functionality for now. It is recommended that"
|
||||||
|
echo "local or known test servers are used, but it should work with the default servers:"
|
||||||
|
echo " - Google Open DNS for TCP and UDP only "
|
||||||
|
echo "- the getdnsapi.net test server Open Resolver for TLS, STARTTLS, TCP and UDP"
|
||||||
|
echo
|
||||||
|
echo "usage: test_transport.sh"
|
||||||
|
echo " -s server configured for only TCP and UDP"
|
||||||
|
echo " -t server configured for TLS, STARTTLS, TCP and UDP"
|
||||||
|
}
|
||||||
|
|
||||||
|
while getopts ":s:t:dh" opt; do
|
||||||
|
case $opt in
|
||||||
|
d ) set -x ;;
|
||||||
|
s ) SERVER_IP=$OPTARG ; echo "Setting server to $OPTARG" ;;
|
||||||
|
t ) TLS_SERVER_IP=$OPTARG ; echo "Setting TLS server to $OPTARG" ;;
|
||||||
|
h ) usage ; exit ;;
|
||||||
|
esac
|
||||||
|
done
|
||||||
|
|
||||||
|
GOOD_QUERIES=(
|
||||||
|
"-s -A -q getdnsapi.net -l U @${SERVER_IP} "
|
||||||
|
"-s -A -q getdnsapi.net -l T @${SERVER_IP} "
|
||||||
|
"-s -A -q getdnsapi.net -l L @${TLS_SERVER_IP}"
|
||||||
|
"-s -A -q getdnsapi.net -l S @${TLS_SERVER_IP}")
|
||||||
|
|
||||||
|
GOOD_FALLBACK_QUERIES=(
|
||||||
|
"-s -A -q getdnsapi.net -l LT @${SERVER_IP}"
|
||||||
|
"-s -A -q getdnsapi.net -l LU @${SERVER_IP}"
|
||||||
|
"-s -A -q getdnsapi.net -l L @${SERVER_IP} @${TLS_SERVER_IP}"
|
||||||
|
"-s -G -q DNSKEY getdnsapi.net -l UT @${SERVER_IP} -b 512 -D")
|
||||||
|
|
||||||
|
NOT_AVAILABLE_QUERIES=(
|
||||||
|
"-s -A -q getdnsapi.net -l L @${SERVER_IP} "
|
||||||
|
"-s -A -q getdnsapi.net -l S @${SERVER_IP} "
|
||||||
|
"-s -G -q DNSKEY getdnsapi.net -l U @${SERVER_IP} -b 512 -D")
|
||||||
|
|
||||||
|
echo "Starting transport test"
|
||||||
|
echo
|
||||||
|
for (( i = 0; i < 2; i+=1 )); do
|
||||||
|
if [[ i -eq 0 ]]; then
|
||||||
|
echo "**SYNC Mode**"
|
||||||
|
else
|
||||||
|
echo
|
||||||
|
echo "**ASYNC Mode**"
|
||||||
|
SYNC_MODE=" -a "
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "*Success cases:"
|
||||||
|
for (( j = 0; j < ${#GOOD_QUERIES[@]}; j+=1 )); do
|
||||||
|
check_good "`$DIR/getdns_query $SYNC_MODE ${GOOD_QUERIES[${j}]} 2>/dev/null`"
|
||||||
|
echo "getdns_query $SYNC_MODE ${GOOD_QUERIES[${j}]}"
|
||||||
|
(( COUNT++ ))
|
||||||
|
done
|
||||||
|
|
||||||
|
echo "*Success fallback cases:"
|
||||||
|
for (( j = 0; j < ${#GOOD_FALLBACK_QUERIES[@]}; j+=1 )); do
|
||||||
|
check_good "`$DIR/getdns_query $SYNC_MODE ${GOOD_FALLBACK_QUERIES[${j}]} 2>/dev/null`"
|
||||||
|
echo "getdns_query $SYNC_MODE ${GOOD_FALLBACK_QUERIES[${j}]}"
|
||||||
|
(( COUNT++ ))
|
||||||
|
done
|
||||||
|
|
||||||
|
echo "*Transport not available cases:"
|
||||||
|
for (( j = 0; j < ${#NOT_AVAILABLE_QUERIES[@]}; j+=1 )); do
|
||||||
|
check_bad "`$DIR/getdns_query $SYNC_MODE ${NOT_AVAILABLE_QUERIES[${j}]} 2>&1`"
|
||||||
|
echo "getdns_query $SYNC_MODE ${NOT_AVAILABLE_QUERIES[${j}]}"
|
||||||
|
(( COUNT++ ))
|
||||||
|
done
|
||||||
|
done
|
||||||
|
|
||||||
|
echo
|
||||||
|
echo "Finished transport test: did $COUNT queries, $GOOD_COUNT passes, $FAIL_COUNT failures"
|
||||||
|
echo
|
16
src/stub.c
16
src/stub.c
|
@ -370,6 +370,7 @@ tcp_connect(getdns_upstream *upstream, getdns_transport_list_t transport)
|
||||||
static int
|
static int
|
||||||
tcp_connected(getdns_upstream *upstream) {
|
tcp_connected(getdns_upstream *upstream) {
|
||||||
/* Already tried and failed, so let the fallback code take care of things */
|
/* Already tried and failed, so let the fallback code take care of things */
|
||||||
|
/* TODO: We _should_ use a timeout on the TCP handshake*/
|
||||||
if (upstream->fd == -1 || upstream->tcp.write_error != 0)
|
if (upstream->fd == -1 || upstream->tcp.write_error != 0)
|
||||||
return STUB_TCP_ERROR;
|
return STUB_TCP_ERROR;
|
||||||
|
|
||||||
|
@ -448,6 +449,7 @@ static int
|
||||||
tls_cleanup(getdns_upstream *upstream)
|
tls_cleanup(getdns_upstream *upstream)
|
||||||
{
|
{
|
||||||
DEBUG_STUB("*** %s\n", __FUNCTION__);
|
DEBUG_STUB("*** %s\n", __FUNCTION__);
|
||||||
|
if (upstream->tls_obj != NULL)
|
||||||
SSL_free(upstream->tls_obj);
|
SSL_free(upstream->tls_obj);
|
||||||
upstream->tls_obj = NULL;
|
upstream->tls_obj = NULL;
|
||||||
upstream->tls_hs_state = GETDNS_HS_FAILED;
|
upstream->tls_hs_state = GETDNS_HS_FAILED;
|
||||||
|
@ -1376,10 +1378,10 @@ upstream_write_cb(void *userarg)
|
||||||
/* Unqueue the netreq from the write_queue */
|
/* Unqueue the netreq from the write_queue */
|
||||||
if (!(upstream->write_queue = netreq->write_queue_tail)) {
|
if (!(upstream->write_queue = netreq->write_queue_tail)) {
|
||||||
upstream->write_queue_last = NULL;
|
upstream->write_queue_last = NULL;
|
||||||
GETDNS_CLEAR_EVENT(upstream->loop, &upstream->event);
|
|
||||||
upstream->event.write_cb = NULL;
|
upstream->event.write_cb = NULL;
|
||||||
/* Reschedule (if already reading) to clear writable */
|
/* Reschedule (if already reading) to clear writable */
|
||||||
if (upstream->event.read_cb) {
|
if (upstream->event.read_cb) {
|
||||||
|
GETDNS_CLEAR_EVENT(upstream->loop, &upstream->event);
|
||||||
GETDNS_SCHEDULE_EVENT(upstream->loop,
|
GETDNS_SCHEDULE_EVENT(upstream->loop,
|
||||||
upstream->fd, TIMEOUT_FOREVER,
|
upstream->fd, TIMEOUT_FOREVER,
|
||||||
&upstream->event);
|
&upstream->event);
|
||||||
|
@ -1645,7 +1647,6 @@ upstream_reschedule_events(getdns_upstream *upstream, size_t idle_timeout) {
|
||||||
|
|
||||||
DEBUG_STUB("# %s: %p %d\n", __FUNCTION__, upstream, upstream->fd);
|
DEBUG_STUB("# %s: %p %d\n", __FUNCTION__, upstream, upstream->fd);
|
||||||
int reschedule = 0;
|
int reschedule = 0;
|
||||||
GETDNS_CLEAR_EVENT(upstream->loop, &upstream->event);
|
|
||||||
if (!upstream->write_queue && upstream->event.write_cb) {
|
if (!upstream->write_queue && upstream->event.write_cb) {
|
||||||
upstream->event.write_cb = NULL;
|
upstream->event.write_cb = NULL;
|
||||||
reschedule = 1;
|
reschedule = 1;
|
||||||
|
@ -1663,6 +1664,7 @@ upstream_reschedule_events(getdns_upstream *upstream, size_t idle_timeout) {
|
||||||
reschedule = 1;
|
reschedule = 1;
|
||||||
}
|
}
|
||||||
if (reschedule) {
|
if (reschedule) {
|
||||||
|
GETDNS_CLEAR_EVENT(upstream->loop, &upstream->event);
|
||||||
if (upstream->event.read_cb || upstream->event.write_cb)
|
if (upstream->event.read_cb || upstream->event.write_cb)
|
||||||
GETDNS_SCHEDULE_EVENT(upstream->loop,
|
GETDNS_SCHEDULE_EVENT(upstream->loop,
|
||||||
upstream->fd, TIMEOUT_FOREVER, &upstream->event);
|
upstream->fd, TIMEOUT_FOREVER, &upstream->event);
|
||||||
|
@ -1775,12 +1777,18 @@ priv_getdns_submit_stub_request(getdns_network_req *netreq)
|
||||||
case GETDNS_TRANSPORT_TCP:
|
case GETDNS_TRANSPORT_TCP:
|
||||||
upstream_schedule_netreq(netreq->upstream, netreq);
|
upstream_schedule_netreq(netreq->upstream, netreq);
|
||||||
/* TODO[TLS]: Change scheduling for sync calls. */
|
/* TODO[TLS]: Change scheduling for sync calls. */
|
||||||
|
/* For TLS, set a short timeout to catch setup problems. This is reset
|
||||||
|
when the connection is successful.*/
|
||||||
GETDNS_CLEAR_EVENT(dnsreq->loop, &netreq->event);
|
GETDNS_CLEAR_EVENT(dnsreq->loop, &netreq->event);
|
||||||
GETDNS_SCHEDULE_EVENT(
|
GETDNS_SCHEDULE_EVENT(
|
||||||
dnsreq->loop, netreq->upstream->fd, dnsreq->context->timeout,
|
dnsreq->loop, netreq->upstream->fd, /*dnsreq->context->timeout,*/
|
||||||
|
(transport == GETDNS_TRANSPORT_TLS ?
|
||||||
|
dnsreq->context->timeout / 2 : dnsreq->context->timeout),
|
||||||
getdns_eventloop_event_init(&netreq->event, netreq, NULL,
|
getdns_eventloop_event_init(&netreq->event, netreq, NULL,
|
||||||
( dnsreq->loop != netreq->upstream->loop /* Synchronous lookup? */
|
( dnsreq->loop != netreq->upstream->loop /* Synchronous lookup? */
|
||||||
? netreq_upstream_write_cb : NULL), stub_timeout_cb));
|
? netreq_upstream_write_cb : NULL),
|
||||||
|
( transport == GETDNS_TRANSPORT_TLS ?
|
||||||
|
stub_tls_timeout_cb : stub_timeout_cb)));
|
||||||
|
|
||||||
return GETDNS_RETURN_GOOD;
|
return GETDNS_RETURN_GOOD;
|
||||||
default:
|
default:
|
||||||
|
|
|
@ -272,16 +272,16 @@ void callback(getdns_context *context, getdns_callback_type_t callback_type,
|
||||||
free(response_str);
|
free(response_str);
|
||||||
}
|
}
|
||||||
fprintf(stdout,
|
fprintf(stdout,
|
||||||
"Result: The callback with ID %llu was successfull.\n",
|
"Response code was: GOOD. Status was: Callback with ID %llu was successfull.\n",
|
||||||
(unsigned long long)trans_id);
|
(unsigned long long)trans_id);
|
||||||
|
|
||||||
} else if (callback_type == GETDNS_CALLBACK_CANCEL)
|
} else if (callback_type == GETDNS_CALLBACK_CANCEL)
|
||||||
fprintf(stderr,
|
fprintf(stderr,
|
||||||
"Result: The callback with ID %llu was cancelled. Exiting.\n",
|
"An error occurred: The callback with ID %llu was cancelled. Exiting.\n",
|
||||||
(unsigned long long)trans_id);
|
(unsigned long long)trans_id);
|
||||||
else {
|
else {
|
||||||
fprintf(stderr,
|
fprintf(stderr,
|
||||||
"Result: The callback got a callback_type of %d. Exiting.\n",
|
"An error occurred: The callback got a callback_type of %d. Exiting.\n",
|
||||||
callback_type);
|
callback_type);
|
||||||
fprintf(stderr,
|
fprintf(stderr,
|
||||||
"Error : '%s'\n",
|
"Error : '%s'\n",
|
||||||
|
|
Loading…
Reference in New Issue