diff --git a/.gitignore b/.gitignore index 5f9c9492..d53a4dba 100644 --- a/.gitignore +++ b/.gitignore @@ -31,4 +31,6 @@ tests_dict tests_list tests_stub_async tests_stub_sync - +src/example/example-reverse +src/test/check_getdns.log +check_getdns diff --git a/doc/check_getdns_testcases.doc b/doc/check_getdns_testcases.doc new file mode 100644 index 00000000..12d277f5 Binary files /dev/null and b/doc/check_getdns_testcases.doc differ diff --git a/src/test/Makefile.in b/src/test/Makefile.in index b16ca313..9dbdbe55 100644 --- a/src/test/Makefile.in +++ b/src/test/Makefile.in @@ -18,8 +18,8 @@ VPATH = @srcdir@ CC=gcc CFLAGS=@CFLAGS@ -Wall -I$(srcdir)/ -I$(srcdir)/../ -I/usr/local/include -std=c99 $(cflags) LDFLAGS=@LDFLAGS@ -L. -L.. -L/usr/local/lib -LDLIBS=-lgetdns @LIBS@ -PROGRAMS=tests_dict tests_list tests_stub_async tests_stub_sync +LDLIBS=-lgetdns @LIBS@ -lcheck +PROGRAMS=tests_dict tests_list tests_stub_async tests_stub_sync check_getdns .SUFFIXES: .c .o .a .lo .h @@ -40,7 +40,13 @@ tests_stub_async: tests_stub_async.o testmessages.o $(LIBTOOL) --tag=CC --mode=link $(CC) $(CFLAGS) $(LDFLAGS) $(LDLIBS) -o $@ tests_stub_async.o testmessages.o tests_stub_sync: tests_stub_sync.o - $(LIBTOOL) --tag=CC --mode=link $(CC) $(CFLAGS) $(LDFLAGS) $(LDLIBS) -o $@ tests_stub_sync.o + $(LIBTOOL) --tag=CC --mode=link $(CC) $(CFLAGS) $(LDFLAGS) $(LDLIBS) -o $@ tests_stub_sync.o + +check_getdns_common: check_getdns_common.o + $(LIBTOOL) --tag=CC --mode=link $(CC) $(CFLAGS) $(LDFLAGS) $(LDLIBS) -o $@ check_getdns_common.o + +check_getdns: check_getdns.o check_getdns_common.o + $(LIBTOOL) --tag=CC --mode=link $(CC) $(CFLAGS) $(LDFLAGS) $(LDLIBS) -o $@ $^ test: all ./testscript.sh diff --git a/src/test/check_getdns.c b/src/test/check_getdns.c new file mode 100644 index 00000000..8a5bb315 --- /dev/null +++ b/src/test/check_getdns.c @@ -0,0 +1,88 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include "check_getdns_libevent.h" +#include "check_getdns_common.h" +#include "check_getdns_general.h" +#include "check_getdns_general_sync.h" +#include "check_getdns_context_create.h" +#include "check_getdns_context_destroy.h" +#include "check_getdns_cancel_callback.h" +#include "check_getdns_address_sync.h" +#include "check_getdns_list_get_length.h" +#include "check_getdns_list_get_data_type.h" +#include "check_getdns_dict_get_names.h" +#include "check_getdns_dict_get_data_type.h" +#include "check_getdns_dict_get_dict.h" +#include "check_getdns_dict_get_list.h" +#include "check_getdns_dict_get_bindata.h" +#include "check_getdns_dict_get_int.h" +#include "check_getdns_dict_destroy.h" +#include "check_getdns_dict_set_dict.h" +#include "check_getdns_dict_set_list.h" +#include "check_getdns_dict_set_bindata.h" +#include "check_getdns_dict_set_int.h" +#include "check_getdns_convert_ulabel_to_alabel.h" +#include "check_getdns_convert_alabel_to_ulabel.h" + +int +main (void) +{ + int number_failed; + SRunner *sr ; + + Suite *getdns_general_suite(void); + Suite *getdns_general_sync_suite(void); + Suite *getdns_address_sync_suite(void); + Suite *getdns_context_create_suite(void); + Suite *getdns_context_destroy_suite(void); + Suite *getdns_cancel_callback_suite(void); + Suite *getdns_list_get_length_suite(void); + Suite *getdns_list_get_data_type_suite(void); + Suite *getdns_dict_get_names_suite(void); + Suite *getdns_dict_get_data_type_suite(void); + Suite *getdns_dict_get_dict_suite(void); + Suite *getdns_dict_get_list_suite(void); + Suite *getdns_dict_get_bindata_suite(void); + Suite *getdns_dict_get_int_suite(void); + Suite *getdns_dict_destroy_suite(void); + Suite *getdns_dict_set_dict_suite(void); + Suite *getdns_dict_set_list_suite(void); + Suite *getdns_dict_set_bindata_suite(void); + Suite *getdns_dict_set_int_suite(void); + Suite *getdns_convert_ulabel_to_alabel_suite(void); + Suite *getdns_convert_alabel_to_ulabel_suite(void); + + sr = srunner_create(getdns_general_suite()); + srunner_add_suite(sr, getdns_general_sync_suite()); + srunner_add_suite(sr, getdns_address_sync_suite()); + srunner_add_suite(sr, getdns_context_create_suite()); + srunner_add_suite(sr, getdns_context_destroy_suite()); + srunner_add_suite(sr, getdns_cancel_callback_suite()); + srunner_add_suite(sr, getdns_list_get_length_suite()); + srunner_add_suite(sr, getdns_list_get_data_type_suite()); + srunner_add_suite(sr, getdns_dict_get_names_suite()); + srunner_add_suite(sr, getdns_dict_get_data_type_suite()); + srunner_add_suite(sr, getdns_dict_get_dict_suite()); + srunner_add_suite(sr, getdns_dict_get_list_suite()); + srunner_add_suite(sr, getdns_dict_get_bindata_suite()); + srunner_add_suite(sr, getdns_dict_get_int_suite()); + srunner_add_suite(sr, getdns_dict_destroy_suite()); + srunner_add_suite(sr, getdns_dict_set_dict_suite()); + srunner_add_suite(sr, getdns_dict_set_list_suite()); + srunner_add_suite(sr, getdns_dict_set_bindata_suite()); + srunner_add_suite(sr, getdns_dict_set_int_suite()); + srunner_add_suite(sr, getdns_convert_ulabel_to_alabel_suite()); + srunner_add_suite(sr, getdns_convert_alabel_to_ulabel_suite()); + + srunner_set_log(sr, "check_getdns.log"); + srunner_run_all(sr, CK_NORMAL); + number_failed = srunner_ntests_failed(sr); + srunner_free(sr); + return (number_failed == 0) ? EXIT_SUCCESS : EXIT_FAILURE; +} diff --git a/src/test/check_getdns_address_sync.h b/src/test/check_getdns_address_sync.h new file mode 100644 index 00000000..59f937ce --- /dev/null +++ b/src/test/check_getdns_address_sync.h @@ -0,0 +1,297 @@ +#ifndef _check_getdns_address_h_ +#define _check_getdns_address_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ A D D R E S S _ S Y N C * + * * + ************************************************************************** + */ + + START_TEST (getdns_address_sync_1) + { + /* + * context = NULL + * expect: GETDNS_RETURN_BAD_CONTEXT + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + ASSERT_RC(getdns_address_sync(context, "google.com", NULL, &response), + GETDNS_RETURN_BAD_CONTEXT, "Return code from getdns_address_sync()"); + } + END_TEST + + START_TEST (getdns_address_sync_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, NULL, NULL, &response), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_address_sync()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_3) + { + /* + * name = invalid domain (label too long) + * expect: GETDNS_RETURN_BAD_DOMAIN_NAME + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + const char *name = "this.domain.hasalabelwhichexceedsthemaximumdnslabelsizeofsixtythreecharacters.com"; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, name, NULL, &response), + GETDNS_RETURN_BAD_DOMAIN_NAME, "Return code from getdns_address_sync()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_4) + { + /* + * response = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_context *context = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "google.com", NULL, NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_address_sync()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_5) + { + /* + * name = "google.com" + * expect: NOERROR response: + * status = GETDNS_RETURN_GOOD + * rcode = 0 + todo: create zonefile with exact count + * ancount = tbd (number of records in ANSWER section) + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "google.com", NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_address_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_6) + { + /* + * name = "localhost" + * expect: NOERROR response: + * expect: GETDNS_RETURN_GOOD + * rcode = 0 + todo: investigate that proper search order is set for resolution (is local being checked) + todo: create zonefile with exact count + * ancount = tbd (number of records in ANSWER section) + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "localhost", NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_address_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_7) + { + /* + * name = "google.joe" + * status = GETDNS_RETURN_GOOD for NXDOMAIN + * expect: NXDOMAIN response with SOA record + * rcode = 0 + todo: investigate that proper search order is set for resolution (is local being checked) + todo: create host file with exact count + * ancount >= 1 (number of records in ANSWER section) + * and one SOA record ("type": 6) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "google.joe", NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_address_sync()"); + + EXTRACT_RESPONSE; + + assert_nxdomain(&ex_response); + assert_nodata(&ex_response); + assert_soa_in_authority(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_8) + { + /* + * name = "hampster.com" need to replace this with domain from unbound zone + * expect: NOERROR/NODATA response: + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount = 0 (number of records in ANSWER section) + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "hampster.com", NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_address_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_9) + { + /* + * name = "google.com" need to swap this out for max domain name length with max lable length` + * expect: NOERROR response with A records + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount >= 11 (number of records in ANSWER section) + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "google.com", NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_address_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_address_in_answer(&ex_response, TRUE, FALSE); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_10) + { + /* + * name = "75.101.146.66" need to change this to local unbound data + * status = GETDNS_RETURN_GOOD for NXDOMAIN + * expect: NXDOMAIN response with SOA record for NUMERICAL data + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and one SOA record ("type": 6) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "75.101.146.66", NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_address_sync()"); + + EXTRACT_RESPONSE; + + assert_nxdomain(&ex_response); + assert_nodata(&ex_response); + assert_soa_in_authority(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_address_sync_11) + { + /* + * name = "2607:f8b0:4006:802::1007" need to change this to local unbound data + * status = GETDNS_RETURN_GOOD for NXDOMAIN + * expect: NXDOMAIN response with SOA record for NUMERICAL data + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and one SOA record ("type": 6) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_address_sync(context, "2607:f8b0:4006:802::1007", NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_address_sync()"); + + EXTRACT_RESPONSE; + + assert_nxdomain(&ex_response); + assert_nodata(&ex_response); + assert_soa_in_authority(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + Suite * + getdns_address_sync_suite (void) + { + Suite *s = suite_create ("getdns_address_sync()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_address_sync_1); + tcase_add_test(tc_neg, getdns_address_sync_2); + tcase_add_test(tc_neg, getdns_address_sync_3); + tcase_add_test(tc_neg, getdns_address_sync_4); + tcase_add_test(tc_neg, getdns_address_sync_5); + suite_add_tcase(s, tc_neg); + /* Positive test cases */ + + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_address_sync_6); + tcase_add_test(tc_pos, getdns_address_sync_7); + tcase_add_test(tc_pos, getdns_address_sync_8); + tcase_add_test(tc_pos, getdns_address_sync_9); + tcase_add_test(tc_pos, getdns_address_sync_10); + tcase_add_test(tc_pos, getdns_address_sync_11); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_cancel_callback.h b/src/test/check_getdns_cancel_callback.h new file mode 100644 index 00000000..7ff5bc5f --- /dev/null +++ b/src/test/check_getdns_cancel_callback.h @@ -0,0 +1,456 @@ +#ifndef _check_getdns_cancel_callback_h_ +#define _check_getdns_cancel_callback_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ C A N C E L _ C A L L B A C K * + * * + ************************************************************************** + */ + + START_TEST (getdns_cancel_callback_1) + { + /* + * context = NULL + * expect: GETDNS_RETURN_BAD_CONTEXT + */ + getdns_transaction_t transaction_id = 0; + + ASSERT_RC(getdns_cancel_callback(NULL, transaction_id), + GETDNS_RETURN_BAD_CONTEXT, "Return code from getdns_cancel_callback()"); + } + END_TEST + + START_TEST (getdns_cancel_callback_2) + { + /* + * transaction_id corresponds to callback that has already been called + * expect: GETDNS_RETURN_UNKNOWN_TRANSACTION + */ + void verify_getdns_cancel_callback(struct extracted_response *ex_response); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + verify_getdns_cancel_callback, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + + ck_assert_msg(callback_called == 1, "callback_called should == 1, got %d", callback_called); + + ASSERT_RC(getdns_cancel_callback(context, transaction_id), + GETDNS_RETURN_UNKNOWN_TRANSACTION, "Return code from getdns_cancel_callback()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_cancel_callback_3) + { + /* + * transaction_id is unknown + * expect: GETDNS_RETURN_UNKNOWN_TRANSACTION + */ + void verify_getdns_cancel_callback(struct extracted_response *ex_response); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + verify_getdns_cancel_callback, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + + ck_assert_msg(callback_called == 1, "callback_called should == 1, got %d", callback_called); + + transaction_id++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id), + GETDNS_RETURN_UNKNOWN_TRANSACTION, "Return code from getdns_cancel_callback()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_cancel_callback_4) + { + /* + * getdns_cancel_callback() called with transaction_id returned from getdns_general() + * + * if transaction_id is odd, callback is canceled before event loop + * expect: GETDNS_RETURN_GOOD + * if transaction_id is even, callback is canceled after event loop + * expect: GETDNS_RETURN_UNKNOWN_TRANSACTION + * + * expect: callback to be called with GETDNS_CALLBACK_CANCELED (if canceled) + * or GETDNS_CALLBACK_COMPLETE (if not canceled). + */ + void cancel_callbackfn( + struct getdns_context *context, + uint16_t callback_type, + struct getdns_dict *response, + void *userarg, + getdns_transaction_t transaction_id); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + getdns_transaction_t transaction_id_array[10] = {}; + int i; + int odd = 0; + int even = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + for(i = 0; i < 10; i++) + { + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + NULL, &transaction_id, cancel_callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + transaction_id_array[i] = transaction_id; + + /* + * Cancel callback if transaction_id is odd which should be accepted + */ + if(transaction_id % 2) + { + odd++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id), + GETDNS_RETURN_GOOD, "Return code from getdns_cancel_callback()"); + } + } + + RUN_EVENT_LOOP; + + /* + * Cancel the callback for even transaction_ids which should be complete + */ + for(i = 0; i < 10; i++) + { + if((transaction_id_array[i] % 2) == 0) + { + even++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id_array[i]), + GETDNS_RETURN_UNKNOWN_TRANSACTION, "Return code from getdns_cancel_callback()"); + } + } + + ck_assert_msg(callback_called == 10, "callback_called should == 10, got: %d", callback_called); + ck_assert_msg(callback_completed == even, "callback_completed should == %d, got: %d", even, callback_completed); + ck_assert_msg(callback_canceled == odd, "callback_canceled should == %d, got: %d", odd, callback_canceled); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_cancel_callback_5) + { + /* + * getdns_cancel_callback() called with transaction_id returned from getdns_address() + * + * if transaction_id is odd, callback is canceled before event loop + * expect: GETDNS_RETURN_GOOD + * if transaction_id is even, callback is canceled after event loop + * expect: GETDNS_RETURN_UNKNOWN_TRANSACTION + * + * expect: callback to be called with GETDNS_CALLBACK_CANCELED (if canceled) + * or GETDNS_CALLBACK_COMPLETE (if not canceled). + */ + void cancel_callbackfn( + struct getdns_context *context, + uint16_t callback_type, + struct getdns_dict *response, + void *userarg, + getdns_transaction_t transaction_id); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + getdns_transaction_t transaction_id_array[10] = {}; + int i; + int odd = 0; + int even = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + for(i = 0; i < 10; i++) + { + ASSERT_RC(getdns_address(context, "8.8.8.8", NULL, + NULL, &transaction_id, cancel_callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_address()"); + + transaction_id_array[i] = transaction_id; + + /* + * Cancel callback if transaction_id is odd which should be accepted + */ + if(transaction_id % 2) + { + odd++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id), + GETDNS_RETURN_GOOD, "Return code from getdns_cancel_callback()"); + } + } + + RUN_EVENT_LOOP; + + /* + * Cancel the callback for even transaction_ids which should be complete + */ + for(i = 0; i < 10; i++) + { + if((transaction_id_array[i] % 2) == 0) + { + even++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id_array[i]), + GETDNS_RETURN_UNKNOWN_TRANSACTION, "Return code from getdns_cancel_callback()"); + } + } + + ck_assert_msg(callback_called == 10, "callback_called should == 10, got: %d", callback_called); + ck_assert_msg(callback_completed == even, "callback_completed should == %d, got: %d", even, callback_completed); + ck_assert_msg(callback_canceled == odd, "callback_canceled should == %d, got: %d", odd, callback_canceled); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_cancel_callback_6) + { + /* + * getdns_cancel_callback() called with transaction_id returned from getdns_hostname() + * + * if transaction_id is odd, callback is canceled before event loop + * expect: GETDNS_RETURN_GOOD + * if transaction_id is even, callback is canceled after event loop + * expect: GETDNS_RETURN_UNKNOWN_TRANSACTION + * + * expect: callback to be called with GETDNS_CALLBACK_CANCELED (if canceled) + * or GETDNS_CALLBACK_COMPLETE (if not canceled). + */ + void cancel_callbackfn( + struct getdns_context *context, + uint16_t callback_type, + struct getdns_dict *response, + void *userarg, + getdns_transaction_t transaction_id); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + struct getdns_bindata address_type = { 5, (void *)"IPv4" }; + struct getdns_bindata address_data = { 4, (void *)"\x08\x08\x08\x08" }; + struct getdns_dict *address = NULL; + getdns_transaction_t transaction_id = 0; + getdns_transaction_t transaction_id_array[10] = {}; + int i; + int odd = 0; + int even = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + DICT_CREATE(address); + ASSERT_RC(getdns_dict_set_bindata(address, "address_type", &address_type), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata"); + ASSERT_RC(getdns_dict_set_bindata(address, "address_data", &address_data), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata"); + + for(i = 0; i < 10; i++) + { + ASSERT_RC(getdns_hostname(context, address, NULL, + NULL, &transaction_id, cancel_callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_address()"); + + transaction_id_array[i] = transaction_id; + + /* + * Cancel callback if transaction_id is odd which should be accepted + */ + if(transaction_id % 2) + { + odd++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id), + GETDNS_RETURN_GOOD, "Return code from getdns_cancel_callback()"); + } + } + + RUN_EVENT_LOOP; + + /* + * Cancel the callback for even transaction_ids which should be complete + */ + for(i = 0; i < 10; i++) + { + if((transaction_id_array[i] % 2) == 0) + { + even++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id_array[i]), + GETDNS_RETURN_UNKNOWN_TRANSACTION, "Return code from getdns_cancel_callback()"); + } + } + + ck_assert_msg(callback_called == 10, "callback_called should == 10, got: %d", callback_called); + ck_assert_msg(callback_completed == even, "callback_completed should == %d, got: %d", even, callback_completed); + ck_assert_msg(callback_canceled == odd, "callback_canceled should == %d, got: %d", odd, callback_canceled); + + DICT_DESTROY(address); + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_cancel_callback_7) + { + /* + * getdns_cancel_callback() called with transaction_id returned from getdns_service() + * + * if transaction_id is odd, callback is canceled before event loop + * expect: GETDNS_RETURN_GOOD + * if transaction_id is even, callback is canceled after event loop + * expect: GETDNS_RETURN_UNKNOWN_TRANSACTION + * + * expect: callback to be called with GETDNS_CALLBACK_CANCELED (if canceled) + * or GETDNS_CALLBACK_COMPLETE (if not canceled). + */ + void cancel_callbackfn( + struct getdns_context *context, + uint16_t callback_type, + struct getdns_dict *response, + void *userarg, + getdns_transaction_t transaction_id); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + getdns_transaction_t transaction_id_array[10] = {}; + int i; + int odd = 0; + int even = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + for(i = 0; i < 10; i++) + { + ASSERT_RC(getdns_service(context, "google.com", NULL, + NULL, &transaction_id, cancel_callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_service()"); + + transaction_id_array[i] = transaction_id; + + /* + * Cancel callback if transaction_id is odd which should be accepted + */ + if(transaction_id % 2) + { + odd++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id), + GETDNS_RETURN_GOOD, "Return code from getdns_cancel_callback()"); + } + } + + RUN_EVENT_LOOP; + + /* + * Cancel the callback for even transaction_ids which should be complete + */ + for(i = 0; i < 10; i++) + { + if((transaction_id_array[i] % 2) == 0) + { + even++; + ASSERT_RC(getdns_cancel_callback(context, transaction_id_array[i]), + GETDNS_RETURN_UNKNOWN_TRANSACTION, "Return code from getdns_cancel_callback()"); + } + } + + ck_assert_msg(callback_called == 10, "callback_called should == 10, got: %d", callback_called); + ck_assert_msg(callback_completed == even, "callback_completed should == %d, got: %d", even, callback_completed); + ck_assert_msg(callback_canceled == odd, "callback_canceled should == %d, got: %d", odd, callback_canceled); + + CONTEXT_DESTROY; + } + END_TEST + + /* + * Callback function for getdns_cancel_callback() tests + * + * callback_type should be GETDNS_CALLBACK_CANCEL for odd transaction_ids + * should be GETDNS_CALLBACK_COMPLETE for even transaction_ids + */ + void cancel_callbackfn( + struct getdns_context *context, + uint16_t callback_type, + struct getdns_dict *response, + void *userarg, + getdns_transaction_t transaction_id) + { + callback_called++; + + if(callback_type == GETDNS_CALLBACK_CANCEL) + { + callback_canceled++; + ck_assert_msg(transaction_id % 2, + "Only callbacks with odd transaction_ids were canceled, this one is even: %d", + transaction_id); + } + else if(callback_type == GETDNS_CALLBACK_COMPLETE) + { + callback_completed++; + ck_assert_msg((transaction_id % 2) == 0, + "One callbacks with even transaction_ids should complete, this one is odd: %d", + transaction_id); + } + else + { + if(transaction_id % 2) + ck_abort_msg("callback_type should == GETDNS_CALLBACK_CANCEL for odd transaction_id (%d), got: %d", + transaction_id, callback_type); + else + ck_abort_msg("callback_type should == GETDNS_CALLBACK_COMPLETE for even transaction_id (%d), got %d", + transaction_id, callback_type); + } + } + + /* + * Function passed via userarg to async functions for cancel callback tests + */ + void verify_getdns_cancel_callback(struct extracted_response *ex_response) + { + /* + * increment callback_called global to prove callback was called. + */ + callback_called++; + } + + Suite * + getdns_cancel_callback_suite (void) + { + Suite *s = suite_create ("getdns_cancel_callback()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_cancel_callback_1); + tcase_add_test(tc_neg, getdns_cancel_callback_2); + tcase_add_test(tc_neg, getdns_cancel_callback_3); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_cancel_callback_4); + tcase_add_test(tc_pos, getdns_cancel_callback_5); + tcase_add_test(tc_pos, getdns_cancel_callback_6); + tcase_add_test(tc_pos, getdns_cancel_callback_7); + + suite_add_tcase(s, tc_pos); + return s; + } + +#endif diff --git a/src/test/check_getdns_common.c b/src/test/check_getdns_common.c new file mode 100644 index 00000000..5e5e6281 --- /dev/null +++ b/src/test/check_getdns_common.c @@ -0,0 +1,272 @@ +#include +#include +#include +#include +#include +#include +#include +#include "check_getdns_common.h" + +int callback_called = 0; +int callback_completed = 0; +int callback_canceled = 0; + +/* + * extract_response extracts all of the various information + * a test may want to look at from the response. + */ +void extract_response(struct getdns_dict *response, struct extracted_response *ex_response) +{ + ck_assert_msg(response != NULL, "Response should not be NULL"); + + ASSERT_RC(getdns_dict_get_int(response, "answer_type", &ex_response->top_answer_type), + GETDNS_RETURN_GOOD, "Failed to extract \"top answer_type\""); + + ASSERT_RC(getdns_dict_get_bindata(response, "canonical_name", &ex_response->top_canonical_name), + GETDNS_RETURN_GOOD, "Failed to extract \"top canonical_name\""); + + ASSERT_RC(getdns_dict_get_list(response, "just_address_answers", &ex_response->just_address_answers), + GETDNS_RETURN_GOOD, "Failed to extract \"just_address_answers\""); + ck_assert_msg(ex_response->just_address_answers != NULL, "just_address_answers should not be NULL"); + + ASSERT_RC(getdns_dict_get_list(response, "replies_full", &ex_response->replies_full), + GETDNS_RETURN_GOOD, "Failed to extract \"replies_full\""); + ck_assert_msg(ex_response->replies_full != NULL, "replies_full should not be NULL"); + + ASSERT_RC(getdns_dict_get_list(response, "replies_tree", &ex_response->replies_tree), + GETDNS_RETURN_GOOD, "Failed to extract \"replies_tree\""); + ck_assert_msg(ex_response->replies_tree != NULL, "replies_tree should not be NULL"); + + ASSERT_RC(getdns_list_get_dict(ex_response->replies_tree, 0, &ex_response->replies_tree_sub_dict), + GETDNS_RETURN_GOOD, "Failed to extract \"replies_tree[0]\""); + ck_assert_msg(ex_response->replies_tree_sub_dict != NULL, "replies_tree[0] dict should not be NULL"); + + ASSERT_RC(getdns_dict_get_list(ex_response->replies_tree_sub_dict, "additional", &ex_response->additional), + GETDNS_RETURN_GOOD, "Failed to extract \"additional\""); + ck_assert_msg(ex_response->additional != NULL, "additional should not be NULL"); + + ASSERT_RC(getdns_dict_get_list(ex_response->replies_tree_sub_dict, "answer", &ex_response->answer), + GETDNS_RETURN_GOOD, "Failed to extract \"answer\""); + ck_assert_msg(ex_response->answer != NULL, "answer should not be NULL"); + + ASSERT_RC(getdns_dict_get_int(ex_response->replies_tree_sub_dict, "answer_type", &ex_response->answer_type), + GETDNS_RETURN_GOOD, "Failed to extract \"answer_type\""); + + ASSERT_RC(getdns_dict_get_list(ex_response->replies_tree_sub_dict, "authority", &ex_response->authority), + GETDNS_RETURN_GOOD, "Failed to extract \"authority\""); + ck_assert_msg(ex_response->authority != NULL, "authority should not be NULL"); + + ASSERT_RC(getdns_dict_get_bindata(ex_response->replies_tree_sub_dict, "canonical_name", &ex_response->canonical_name), + GETDNS_RETURN_GOOD, "Failed to extract \"canonical_name\""); + + ASSERT_RC(getdns_dict_get_dict(ex_response->replies_tree_sub_dict, "header", &ex_response->header), + GETDNS_RETURN_GOOD, "Failed to extract \"header\""); + ck_assert_msg(ex_response->header != NULL, "header should not be NULL"); + + ASSERT_RC(getdns_dict_get_dict(ex_response->replies_tree_sub_dict, "question", &ex_response->question), + GETDNS_RETURN_GOOD, "Failed to extract \"question\""); + ck_assert_msg(ex_response->question != NULL, "question should not be NULL"); + + ASSERT_RC(getdns_dict_get_int(response, "status", &ex_response->status), + GETDNS_RETURN_GOOD, "Failed to extract \"status\""); +} + +/* + * assert_noerror asserts that the rcode is 0 + */ +void assert_noerror(struct extracted_response *ex_response) +{ + uint32_t rcode; + + ASSERT_RC(ex_response->status, GETDNS_RESPSTATUS_GOOD, "Unexpected value for \"status\""); + ASSERT_RC(getdns_dict_get_int(ex_response->header, "rcode", &rcode), GETDNS_RETURN_GOOD, "Failed to extract \"rcode\""); + ck_assert_msg(rcode == 0, "Expected rcode == 0, got %d", rcode); +} + +/* + * assert_nodata asserts that ancount in the header and the + * of the answer section (list) are both zero. + */ +void assert_nodata(struct extracted_response *ex_response) +{ + uint32_t ancount; + size_t length; + + ASSERT_RC(getdns_dict_get_int(ex_response->header, "ancount", &ancount), + GETDNS_RETURN_GOOD, "Failed to extract \"ancount\""); + ck_assert_msg(ancount == 0, "Expected ancount == 0, got %d", ancount); + + ASSERT_RC(getdns_list_get_length(ex_response->answer, &length), + GETDNS_RETURN_GOOD, "Failed to extract \"answer\" length"); + ck_assert_msg(length == 0, "Expected \"answer\" length == 0, got %d", length); +} + +/* + * assert_address_records_in_answer asserts that ancount in the header + * is >= 1, ancount is equal to the length of "answer", and that all of + * the records in the answer section are A and/or AAAA resource records + * based on the value of the a/aaaa arguments. + */ +void assert_address_in_answer(struct extracted_response *ex_response, int a, int aaaa) +{ + uint32_t ancount; + size_t length; + struct getdns_dict *rr_dict; + uint32_t type; + uint32_t address_records = 0; + size_t i; + + ASSERT_RC(getdns_dict_get_int(ex_response->header, "ancount", &ancount), + GETDNS_RETURN_GOOD, "Failed to extract \"ancount\""); + ck_assert_msg(ancount >= 1, "Expected ancount >= 1, got %d", ancount); + + ASSERT_RC(getdns_list_get_length(ex_response->answer, &length), + GETDNS_RETURN_GOOD, "Failed to extract \"answer\" length"); + ck_assert_msg(length == ancount, "Expected \"answer\" length == ancount: %d, got %d", ancount, length); + + for(i = 0; i < length; i++) + { + ASSERT_RC(getdns_list_get_dict(ex_response->answer, i, &rr_dict), + GETDNS_RETURN_GOOD, "Failed to extract \"answer\" record"); + ASSERT_RC(getdns_dict_get_int(rr_dict, "type", &type), + GETDNS_RETURN_GOOD, "Failed to extract \"type\" from answer record"); + switch (type) + { + case GETDNS_RRTYPE_A: + if(a && type == GETDNS_RRTYPE_A) + address_records++; + case GETDNS_RRTYPE_AAAA: + if(aaaa && type == GETDNS_RRTYPE_AAAA) + address_records++; + } + } + ck_assert_msg(ancount == address_records, "ancount: %d address records mismatch: %d", + ancount, address_records); +} + +/* + * assert_nxdomain asserts that an NXDOMAIN response was + * was returned for the DNS query meaning: + * rcode == 3 + */ +void assert_nxdomain(struct extracted_response *ex_response) +{ + uint32_t rcode; + + ASSERT_RC(ex_response->status, GETDNS_RESPSTATUS_GOOD, "Unexpected value for \"status\""); + ASSERT_RC(getdns_dict_get_int(ex_response->header, "rcode", &rcode), GETDNS_RETURN_GOOD, "Failed to extract \"rcode\""); + ck_assert_msg(rcode == 3, "Expected rcode == 0, got %d", rcode); +} + +/* + * assert_soa_in_authority asserts that a SOA record was + * returned in the authority sections. + */ +void assert_soa_in_authority(struct extracted_response *ex_response) +{ + uint32_t nscount; + size_t length; + struct getdns_dict *rr_dict; + uint32_t type; + uint32_t soa_records = 0; + size_t i; + + ASSERT_RC(getdns_dict_get_int(ex_response->header, "nscount", &nscount), + GETDNS_RETURN_GOOD, "Failed to extract \"nscount\""); + ck_assert_msg(nscount >= 1, "Expected nscount >= 1, got %d", nscount); + + ASSERT_RC(getdns_list_get_length(ex_response->authority, &length), + GETDNS_RETURN_GOOD, "Failed to extract \"authority\" length"); + ck_assert_msg(length == nscount, "Expected \"authority\" length == nscount: %d, got %d", nscount, length); + + for(i = 0; i < length; i++) + { + ASSERT_RC(getdns_list_get_dict(ex_response->authority, i, &rr_dict), + GETDNS_RETURN_GOOD, "Failed to extract \"authority\" record"); + ASSERT_RC(getdns_dict_get_int(rr_dict, "type", &type), + GETDNS_RETURN_GOOD, "Failed to extract \"type\" from authority record"); + if(type == GETDNS_RRTYPE_SOA) + soa_records++; + } + + ck_assert_msg(soa_records == 1, "Expected to find one SOA record in authority section, got %d", soa_records); +} + +/* + * assert_ptr_in_answer asserts that a PTR record was + * returned in the answer sections. + */ +void assert_ptr_in_answer(struct extracted_response *ex_response) +{ + uint32_t ancount; + size_t length; + struct getdns_dict *rr_dict; + uint32_t type; + uint32_t ptr_records = 0; + size_t i; + + ASSERT_RC(getdns_dict_get_int(ex_response->header, "ancount", &ancount), + GETDNS_RETURN_GOOD, "Failed to extract \"nscount\""); + ck_assert_msg(ancount >= 1, "Expected ancount >= 1, got %d", ancount); + + ASSERT_RC(getdns_list_get_length(ex_response->answer, &length), + GETDNS_RETURN_GOOD, "Failed to extract \"answer\" length"); + ck_assert_msg(length == ancount, "Expected \"answer\" length == ancount: %d, got %d", ancount, length); + + for(i = 0; i < length; i++) + { + ASSERT_RC(getdns_list_get_dict(ex_response->answer, i, &rr_dict), + GETDNS_RETURN_GOOD, "Failed to extract \"answer\" record"); + ASSERT_RC(getdns_dict_get_int(rr_dict, "type", &type), + GETDNS_RETURN_GOOD, "Failed to extract \"type\" from answer record"); + if(type == GETDNS_RRTYPE_PTR) + ptr_records++; + } + + ck_assert_msg(ptr_records == 1, "Expected to find one PTR record in answer section, got %d", ptr_records); +} + +/* + * callbackfn is the callback function given to all + * asynchronous query tests. It is expected to only + * be called for positive tests and will verify the + * response that is returned. + */ +void callbackfn(struct getdns_context *context, + uint16_t callback_type, + struct getdns_dict *response, + void *userarg, + getdns_transaction_t transaction_id) +{ + typedef void (*fn_ptr)(struct extracted_response *ex_response); + fn_ptr fn = userarg; + + /* + * If userarg is NULL, either a negative test case + * erroneously reached the query state, or the value + * in userarg (verification function) was somehow + * lost in transit. + */ + ck_assert_msg(userarg != NULL, "Callback called with NULL userarg"); + + /* + * We expect the callback type to be COMPLETE. + */ + ASSERT_RC(callback_type, GETDNS_CALLBACK_COMPLETE, "Callback type"); + + /* + printf("DICT:\n%s\n", getdns_pretty_print_dict(response)); + */ + + /* + * Extract the response. + */ + EXTRACT_RESPONSE; + + /* + * Call the response verification function that + * was passed via userarg. + */ + fn(&ex_response); + +} diff --git a/src/test/check_getdns_common.h b/src/test/check_getdns_common.h new file mode 100644 index 00000000..5b64d223 --- /dev/null +++ b/src/test/check_getdns_common.h @@ -0,0 +1,177 @@ +#ifndef _check_getdns_common_h_ +#define _check_getdns_common_h_ + + #define TRUE 1 + #define FALSE 0 + #define MAXLEN 200 + + extern int callback_called; + extern int callback_completed; + extern int callback_canceled; + + struct extracted_response { + uint32_t top_answer_type; + struct getdns_bindata *top_canonical_name; + struct getdns_list *just_address_answers; + struct getdns_list *replies_full; + struct getdns_list *replies_tree; + struct getdns_dict *replies_tree_sub_dict; + struct getdns_list *additional; + struct getdns_list *answer; + uint32_t answer_type; + struct getdns_list *authority; + struct getdns_bindata *canonical_name; + struct getdns_dict *header; + struct getdns_dict *question; + uint32_t status; + }; + + /* + * The ASSERT_RC macro is used to assert + * whether the return code from the last + * getdns API call is what was expected. + */ + #define ASSERT_RC(rc, expected_rc, prefix) \ + { \ + size_t buflen = MAXLEN; \ + char error_string[MAXLEN]; \ + getdns_return_t evaluated_rc = rc; \ + getdns_strerror(evaluated_rc, error_string, buflen); \ + ck_assert_msg(evaluated_rc == expected_rc, \ + "%s: expecting %s: %d, but received: %d: %s", \ + prefix, #expected_rc, expected_rc, evaluated_rc, error_string); \ + } + + /* + * The CONTEXT_CREATE macro is used to + * create a context and assert the proper + * return code is returned. + */ + #define CONTEXT_CREATE(set_from_os) \ + ASSERT_RC(getdns_context_create(&context, set_from_os), \ + GETDNS_RETURN_GOOD, \ + "Return code from getdns_context_create()"); + + /* + * The CONTEXT_FREE macro is used to + * destroy the current context. + */ + #define CONTEXT_DESTROY getdns_context_destroy(context); + + /* + * The EVENT_BASE_CREATE macro is used to + * create an event base and put it in the + * context. + */ + #define EVENT_BASE_CREATE \ + event_base = event_base_new(); \ + ck_assert_msg(event_base != NULL, "Event base creation failed"); \ + ASSERT_RC(getdns_extension_set_libevent_base(context, event_base), \ + GETDNS_RETURN_GOOD, \ + "Return code from getdns_extension_set_libevent_base()"); + + /* + * The RUN_EVENT_LOOP macro calls the event loop. + */ + #define RUN_EVENT_LOOP event_base_dispatch(event_base); + + /* + * The LIST_CREATE macro simply creates a + * list and verifies the returned pointer + * is not NULL. + */ + #define LIST_CREATE(list) \ + list = getdns_list_create(); \ + ck_assert_msg(list != NULL, \ + "NULL pointer returned by getdns_list_create()"); + + /* + * The LIST_DESTROY macro destroys a list. + */ + #define LIST_DESTROY(list) getdns_list_destroy(list); + + /* + * The DICT_CREATE macro simply creates a + * dict and verifies the returned pointer + * is not NULL. + */ + #define DICT_CREATE(dict) \ + dict = getdns_dict_create(); \ + ck_assert_msg(dict != NULL, \ + "NULL pointer returned by getdns_dict_create()"); + + /* + * The DICT_DESTROY macro destroys a dict. + */ + #define DICT_DESTROY(dict) getdns_dict_destroy(dict); + + /* + * The process_response macro declares the + * variables needed to house the response and + * calls the function that extracts it. + */ + #define EXTRACT_RESPONSE \ + struct extracted_response ex_response; \ + extract_response(response, &ex_response); + + // + // FUNCTION DECLARATIONS + // + + /* + * extract_response extracts all of the various information + * a test may want to look at from the response. + */ + void extract_response(struct getdns_dict *response, struct extracted_response *ex_response); + + /* + * assert_noerror asserts that the rcode is 0. + */ + void assert_noerror(struct extracted_response *ex_response); + + /* + * assert_nodata asserts that ancount in the header and the + * of the answer section (list) are both zero. + */ + void assert_nodata(struct extracted_response *ex_response); + + /* + * assert_address_records_in_answer asserts that ancount in + * the header * is >= 1, ancount is equal to the length + * of "answer", and that all of * the records in the + * answer section are A and/or AAAA resource records based + * on the value of the a/aaaa arguments. + */ + void assert_address_in_answer(struct extracted_response *ex_response, int a, int aaaa); + + /* + * assert_nxdomain asserts that an NXDOMAIN response was + * was returned for the DNS query meaning rcode == 3. + */ + void assert_nxdomain(struct extracted_response *ex_response); + + /* + * assert_soa_in_authority asserts that a SOA record was + * returned in the authority sections. + */ + void assert_soa_in_authority(struct extracted_response *ex_response); + + /* + * assert_ptr_in_answer asserts that a PTR record was + * returned in the answer sections. + */ + void assert_ptr_in_answer(struct extracted_response *ex_response); + + /* + * callbackfn is the callback function given to all + * asynchronous query tests. It is expected to only + * be called for positive tests and will verify the + * response that is returned. + */ + void callbackfn(struct getdns_context *context, + uint16_t callback_type, + struct getdns_dict *response, + void *userarg, + getdns_transaction_t transaction_id); + +#endif diff --git a/src/test/check_getdns_context_create.h b/src/test/check_getdns_context_create.h new file mode 100644 index 00000000..570e87d0 --- /dev/null +++ b/src/test/check_getdns_context_create.h @@ -0,0 +1,73 @@ +#ifndef _check_getdns_context_create_h_ +#define _check_getdns_context_create_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ C O N T E X T _ C R E A T E * + * * + ************************************************************************** + */ + + START_TEST (getdns_context_create_1) + { + /* + * context = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + + ASSERT_RC(getdns_context_create(NULL, TRUE), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_context_create()"); + } + END_TEST + + START_TEST (getdns_context_create_2) + { + /* + * set_from_os = TRUE + * expect: context initialized with operating system info + * GETDNS_RETURN_GOOD + */ + struct getdns_context *context = NULL; + + CONTEXT_CREATE(TRUE); + // TODO: Do something here to verify set_from_os = TRUE + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_context_create_3) + { + /* + * set_from_os = FALSE + * expect: context is not initialized with operating system info + * GETDNS_RETURN_GOOD + */ + struct getdns_context *context = NULL; + + CONTEXT_CREATE(FALSE); + // TODO: Do something here to verify set_from_os = TRUE + CONTEXT_DESTROY; + } + END_TEST + + Suite * + getdns_context_create_suite (void) + { + Suite *s = suite_create ("getdns_context_create()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_context_create_1); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_context_create_2); + tcase_add_test(tc_pos, getdns_context_create_3); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_context_destroy.h b/src/test/check_getdns_context_destroy.h new file mode 100644 index 00000000..f085e2ca --- /dev/null +++ b/src/test/check_getdns_context_destroy.h @@ -0,0 +1,182 @@ +#ifndef _check_getdns_context_destroy_h_ +#define _check_getdns_context_destroy_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ C O N T E X T _ D E S T R O Y * + * * + ************************************************************************** + */ + + START_TEST (getdns_context_destroy_1) + { + /* + * context = NULL + * expect: nothing, no segmentation fault + */ + + getdns_context_destroy(NULL); + } + END_TEST + + START_TEST (getdns_context_destroy_2) + { + /* + * destroy called with valid context and no outstanding transactions + * expect: nothing, context is freed + */ + struct getdns_context *context = NULL; + + CONTEXT_CREATE(TRUE); + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_context_destroy_3) + { + /* + * destroy called immediately following getdns_general + * expect: callback should be called before getdns_context_destroy() returns + */ + void verify_getdns_context_destroy(struct extracted_response *ex_response); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + verify_getdns_context_destroy, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + + ck_assert_msg(callback_called == 1, "callback_called should == 1, got %d", callback_called); + } + END_TEST + + START_TEST (getdns_context_destroy_4) + { + /* + * destroy called immediately following getdns_address + * expect: callback should be called before getdns_context_destroy() returns + */ + void verify_getdns_context_destroy(struct extracted_response *ex_response); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_address(context, "8.8.8.8", NULL, + verify_getdns_context_destroy, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_address()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + + ck_assert_msg(callback_called == 1, "callback_called should == 1, got %d", callback_called); + } + END_TEST + + START_TEST (getdns_context_destroy_5) + { + /* + * destroy called immediately following getdns_address + * expect: callback should be called before getdns_context_destroy() returns + */ + void verify_getdns_context_destroy(struct extracted_response *ex_response); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + struct getdns_bindata address_type = { 5, (void *)"IPv4" }; + struct getdns_bindata address_data = { 4, (void *)"\x08\x08\x08\x08" }; + struct getdns_dict *address = NULL; + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + DICT_CREATE(address); + ASSERT_RC(getdns_dict_set_bindata(address, "address_type", &address_type), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata"); + ASSERT_RC(getdns_dict_set_bindata(address, "address_data", &address_data), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata"); + + ASSERT_RC(getdns_hostname(context, address, NULL, + verify_getdns_context_destroy, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_address()"); + + RUN_EVENT_LOOP; + DICT_DESTROY(address); + CONTEXT_DESTROY; + + ck_assert_msg(callback_called == 1, "callback_called should == 1, got %d", callback_called); + } + END_TEST + + START_TEST (getdns_context_destroy_6) + { + /* + * destroy called immediately following getdns_address + * expect: callback should be called before getdns_context_destroy() returns + */ + void verify_getdns_context_destroy(struct extracted_response *ex_response); + struct getdns_context *context = NULL; + struct event_base *event_base = NULL; + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_service(context, "google.com", NULL, + verify_getdns_context_destroy, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_service()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + + ck_assert_msg(callback_called == 1, "callback_called should == 1, got %d", callback_called); + } + END_TEST + + void verify_getdns_context_destroy(struct extracted_response *ex_response) + { + /* + * Sleep for a second to make getdns_context_destroy() wait. + */ + sleep(1); + + /* + * callback_called is a global and we increment it + * here to show that the callback was called. + */ + callback_called++; + } + + Suite * + getdns_context_destroy_suite (void) + { + Suite *s = suite_create ("getdns_context_destroy()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_context_destroy_1); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_context_destroy_2); + tcase_add_test(tc_pos, getdns_context_destroy_3); + tcase_add_test(tc_pos, getdns_context_destroy_4); + tcase_add_test(tc_pos, getdns_context_destroy_5); + tcase_add_test(tc_pos, getdns_context_destroy_6); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_convert_alabel_to_ulabel.h b/src/test/check_getdns_convert_alabel_to_ulabel.h new file mode 100644 index 00000000..060d545b --- /dev/null +++ b/src/test/check_getdns_convert_alabel_to_ulabel.h @@ -0,0 +1,74 @@ +#ifndef _check_getdns_convert_alabel_to_ulabel_h_ +#define _check_getdns_convert_alabel_to_ulabel_h_ + + /* + ************************************************************************************* + * * + * T E S T S F O R G E T D N S _ C O N V E R T _ A L A B E L _ T O _ U L A B E L * + * * + ************************************************************************************* + */ + + START_TEST (getdns_convert_alabel_to_ulabel_1) + { + /* + * alabel = NULL + * expect: GETDNS_RETURN_GENERIC_ERROR + */ + char *alabel = NULL; + + ck_assert_msg(strcmp( getdns_convert_alabel_to_ulabel( alabel ), "nil" ) == 0, + "Was not expecting %s from getdns_convert_alabel_to_ulabel()", getdns_convert_alabel_to_ulabel( alabel ) ); + + } + END_TEST + + START_TEST (getdns_convert_alabel_to_ulabel_2) + { + /* + * alabel = invalid characters + * expect: GETDNS_RETURN_GENERIC_ERROR + */ + char *alabel = "#$%_"; + + ck_assert_msg(strcmp( getdns_convert_alabel_to_ulabel( alabel ), "#$%_" ) == 0, + "Was not expecting %s from getdns_convert_alabel_to_ulabel()", getdns_convert_alabel_to_ulabel( alabel ) ); + + + } + END_TEST + + START_TEST (getdns_convert_alabel_to_ulabel_3) + { + /* + * alabel = valid characters (ace must begin with prefix "xn--" and be followed by a valid puny algorithm output; length limited to 59 chars) + * expect: GETDNS_RETURN_GOOD + */ + char *alabel = "xn--caf-dma"; + + ck_assert_msg(strcmp( getdns_convert_alabel_to_ulabel( alabel ), "café" ) == 0, + "Was not expecting %s from getdns_convert_alabel_to_ulabel()", getdns_convert_alabel_to_ulabel( alabel ) ); + + } + END_TEST + + Suite * + getdns_convert_alabel_to_ulabel_suite (void) + { + Suite *s = suite_create ("getdns_convert_alabel_to_ulabel()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_convert_alabel_to_ulabel_1); + tcase_add_test(tc_neg, getdns_convert_alabel_to_ulabel_2); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_convert_alabel_to_ulabel_3); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_convert_ulabel_to_alabel.h b/src/test/check_getdns_convert_ulabel_to_alabel.h new file mode 100644 index 00000000..06ab19ae --- /dev/null +++ b/src/test/check_getdns_convert_ulabel_to_alabel.h @@ -0,0 +1,71 @@ +#ifndef _check_getdns_convert_ulabel_to_alabel_h_ +#define _check_getdns_convert_ulabel_to_alabel_h_ + + /* + ************************************************************************************* + * * + * T E S T S F O R G E T D N S _ C O N V E R T _ U L A B E L _ T O _ A L A B E L * + * * + ************************************************************************************* + */ + + START_TEST (getdns_convert_ulabel_to_alabel_1) + { + /* + * ulabel = NULL + * expect: GETDNS_RETURN_GENERIC_ERROR + */ + char *ulabel = NULL; + + ck_assert_msg(strcmp( getdns_convert_ulabel_to_alabel( ulabel ), "nil" ) == 0, + "Was not expecting %s from getdns_convert_ulabel_to_alabel()", getdns_convert_ulabel_to_alabel( ulabel ) ); + } + END_TEST + + START_TEST (getdns_convert_ulabel_to_alabel_2) + { + /* + * ulabel = invalid characters + * expect: GETDNS_RETURN_GENERIC_ERROR + */ + char *ulabel = "#$%_"; + + ck_assert_msg(strcmp( getdns_convert_ulabel_to_alabel( ulabel ), "#$%_" ) == 0, + "Was not expecting %s from getdns_convert_ulabel_to_alabel()", getdns_convert_ulabel_to_alabel( ulabel ) ); + } + END_TEST + + START_TEST (getdns_convert_ulabel_to_alabel_3) + { + /* + * ulabel = valid characters ( _abc, -abc, -abc-, abc- and limited to 63 octets ) + * expect: GETDNS_RETURN_GOOD + */ + char *ulabel = "café"; + + ck_assert_msg(strcmp( getdns_convert_ulabel_to_alabel( ulabel ), "xn--caf-dma" ) == 0, + "Was not expecting %s from getdns_convert_ulabel_to_alabel()", getdns_convert_ulabel_to_alabel( ulabel ) ); + + } + END_TEST + + Suite * + getdns_convert_ulabel_to_alabel_suite (void) + { + Suite *s = suite_create ("getdns_convert_ulabel_to_alabel()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_convert_ulabel_to_alabel_1); + tcase_add_test(tc_neg, getdns_convert_ulabel_to_alabel_2); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_convert_ulabel_to_alabel_3); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_destroy.h b/src/test/check_getdns_dict_destroy.h new file mode 100644 index 00000000..d470bc82 --- /dev/null +++ b/src/test/check_getdns_dict_destroy.h @@ -0,0 +1,219 @@ +#ifndef _check_getdns_dict_destroy_h_ +#define _check_getdns_dict_destroy_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ D E S T R O Y * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_destroy_1) + { + /* + * this_dict = NULL + * expect: nothing + */ + struct getdns_dict *this_dict = NULL; + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_destroy_2) + { + /* + * build a complex dict and then destroy it + * + * dict1-> "int" = 1 + * -> "bindata" = { 8, "bindata" } + * -> "dict" = dict2->"int" = 2 + * -> "bindata" = { 8, "bindata" } + * -> "dict" = dict3 -> "int" = 3 + * -> "bindata" = { 8, "bindata" } + * -> "dict" = dict4 -> "int" = 4 + * -> "list" = list1 0: int = 5 + * -> "list" = list2 0: int = 6 + * 1: bindata = { 8, "bindata" } + * 2: dict = dict5 -> "bindata" = { 8, "bindata" } + * 3: list = list3 0: bindata = { 8, "bindata" } + * -> "list" = list4 0: int = 6 + * 1: bindata = { 8, "bindata" } + * 2: dict6 -> "int" = 8 + * -> "bindata" = { 8, "bindata" } + * -> "dict" = dict7 -> "int" = 9 + * -> "list" = list5 0: int = 10 + * 3: list6 0: int = 11 + * 1: bindata = { 8, "bindata" } + * 2: dict8 -> "bindata" = { 8, "bindata" } + * 3: list7 0: bindata = { 8, "bindata" } + * + * expect: nothing + */ + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + struct getdns_list *list7; + struct getdns_dict *dict8; + struct getdns_list *list6; + struct getdns_list *list5; + struct getdns_dict *dict7; + struct getdns_dict *dict6; + struct getdns_list *list4; + struct getdns_list *list3; + struct getdns_dict *dict5; + struct getdns_list *list2; + struct getdns_list *list1; + struct getdns_dict *dict4; + struct getdns_dict *dict3; + struct getdns_dict *dict2; + struct getdns_dict *dict1; + + /* + * Build it backwards, with the deepest elements first. + */ + LIST_CREATE(list7); + ASSERT_RC(getdns_list_set_bindata(list7, 0, &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + DICT_CREATE(dict8); + ASSERT_RC(getdns_dict_set_bindata(dict8, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + LIST_CREATE(list6); + ASSERT_RC(getdns_list_set_int(list6, 0, 11), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_int()"); + ASSERT_RC(getdns_list_set_bindata(list6, 1, &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_bindata()"); + ASSERT_RC(getdns_list_set_dict(list6, 2, dict8), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_dict()"); + ASSERT_RC(getdns_list_set_list(list6, 3, list7), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_list()"); + + LIST_CREATE(list5); + ASSERT_RC(getdns_list_set_int(list5, 0, 10), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_int()"); + + DICT_CREATE(dict7); + ASSERT_RC(getdns_dict_set_int(dict7, "int", 9), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + DICT_CREATE(dict6); + ASSERT_RC(getdns_dict_set_int(dict6, "int", 8), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + ASSERT_RC(getdns_dict_set_bindata(dict6, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + ASSERT_RC(getdns_dict_set_dict(dict6, "dict", dict7), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + ASSERT_RC(getdns_dict_set_list(dict6, "list", list5), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + LIST_CREATE(list4); + ASSERT_RC(getdns_list_set_int(list4, 0, 7), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_int()"); + ASSERT_RC(getdns_list_set_bindata(list4, 1, &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_bindata()"); + ASSERT_RC(getdns_list_set_dict(list4, 2, dict6), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_dict()"); + ASSERT_RC(getdns_list_set_list(list4, 3, list5), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_list()"); + + LIST_CREATE(list3); + ASSERT_RC(getdns_list_set_bindata(list3, 0, &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_bindata()"); + + DICT_CREATE(dict5); + ASSERT_RC(getdns_dict_set_bindata(dict5, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + LIST_CREATE(list2); + ASSERT_RC(getdns_list_set_int(list2, 0, 6), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_int()"); + ASSERT_RC(getdns_list_set_bindata(list2, 1, &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_bindata()"); + ASSERT_RC(getdns_list_set_dict(list2, 2, dict5), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_dict()"); + ASSERT_RC(getdns_list_set_list(list2, 3, list3), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_list()"); + + LIST_CREATE(list1); + ASSERT_RC(getdns_list_set_int(list1, 0, 5), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_int()"); + + DICT_CREATE(dict4); + ASSERT_RC(getdns_dict_set_int(dict4, "int", 4), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + DICT_CREATE(dict3); + ASSERT_RC(getdns_dict_set_int(dict3, "int", 3), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + ASSERT_RC(getdns_dict_set_bindata(dict3, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + ASSERT_RC(getdns_dict_set_dict(dict3, "dict", dict4), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + ASSERT_RC(getdns_dict_set_list(dict3, "list", list1), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + DICT_CREATE(dict2); + ASSERT_RC(getdns_dict_set_int(dict2, "int", 2), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + ASSERT_RC(getdns_dict_set_bindata(dict2, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + ASSERT_RC(getdns_dict_set_dict(dict2, "dict", dict3), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + ASSERT_RC(getdns_dict_set_list(dict2, "list", list2), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + DICT_CREATE(dict1); + ASSERT_RC(getdns_dict_set_int(dict1, "int", 1), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + ASSERT_RC(getdns_dict_set_bindata(dict1, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + ASSERT_RC(getdns_dict_set_dict(dict1, "dict", dict2), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + ASSERT_RC(getdns_dict_set_list(dict1, "list", list4), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + /* + * Destroy all of the sub-dicts and sub-lists + */ + LIST_DESTROY(list7); + DICT_DESTROY(dict8); + LIST_DESTROY(list6); + LIST_DESTROY(list5); + DICT_DESTROY(dict7); + DICT_DESTROY(dict6); + LIST_DESTROY(list4); + LIST_DESTROY(list3); + DICT_DESTROY(dict5); + LIST_DESTROY(list2); + LIST_DESTROY(list1); + DICT_DESTROY(dict4); + DICT_DESTROY(dict3); + DICT_DESTROY(dict2); + + /* + * And now destroy the mother of all ints, bindata, dicts, and lists + */ + DICT_DESTROY(dict1); + } + END_TEST + + Suite * + getdns_dict_destroy_suite (void) + { + Suite *s = suite_create ("getdns_dict_destroy()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_destroy_1); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_destroy_2); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_get_bindata.h b/src/test/check_getdns_dict_get_bindata.h new file mode 100644 index 00000000..70a9a931 --- /dev/null +++ b/src/test/check_getdns_dict_get_bindata.h @@ -0,0 +1,169 @@ +#ifndef _check_getdns_dict_get_bindata_h_ +#define _check_getdns_dict_get_bindata_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ G E T _ B I N D A T A * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_get_bindata_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata *answer = NULL; + + ASSERT_RC(getdns_dict_get_bindata(this_dict, "key", &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_bindata()"); + + } + END_TEST + + START_TEST (getdns_dict_get_bindata_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + struct getdns_bindata *answer = NULL; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_bindata(this_dict, NULL, &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_bindata()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_bindata_3) + { + /* + * name does not exist in dict + * Create a dict + * Create some bindata containing "bindata" and add it to the dict with name = "bindata" + * Call getdns_dict_get_bindata() against the first dict with name = "bindata1" + * expect: GETDNS_RETURN_NO_SUCH_DICT_NAME + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + struct getdns_bindata *answer = NULL; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_bindata(this_dict, "bindata1", &answer), + GETDNS_RETURN_NO_SUCH_DICT_NAME, "Return code from getdns_dict_get_bindata()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_bindata_4) + { + /* + * data type at name is not bindata + * Create a dict with one int (name = "ten", value = 10) + * Call getdns_dict_get_bindata() with name = "ten" + * expect: GETDNS_RETURN_WRONG_TYPE_REQUESTED + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata *answer = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, "ten", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_bindata(this_dict, "ten", &answer), + GETDNS_RETURN_WRONG_TYPE_REQUESTED, "Return code from getdns_dict_get_bindata()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_bindata_5) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_bindata(this_dict, "bindata", NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_bindata()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_bindata_6) + { + /* + * successful get bindata + * Create a dict + * Create some bindata containing "bindata" and add it to the dict with name = "bindata" + * Call getdns_dict_get_bindata() against the first dict with name = "bindata" + * expect: retrieved bindata should == "bindata" + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + struct getdns_bindata *answer = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_bindata(this_dict, "bindata", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_bindata()"); + + ck_assert_msg(answer->size == bindata.size, "Expected bindata size == %d, got: %d", + bindata.size, answer->size); + ck_assert_msg(strcmp((char *)answer->data, (char *)bindata.data) == 0, + "Expected bindata data to be \"%s\", got: \"%s\"", + (char *)bindata.data, (char *)answer->data); + + DICT_DESTROY(this_dict); + } + END_TEST + + Suite * + getdns_dict_get_bindata_suite (void) + { + Suite *s = suite_create ("getdns_dict_get_bindata()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_get_bindata_1); + tcase_add_test(tc_neg, getdns_dict_get_bindata_2); + tcase_add_test(tc_neg, getdns_dict_get_bindata_3); + tcase_add_test(tc_neg, getdns_dict_get_bindata_4); + tcase_add_test(tc_neg, getdns_dict_get_bindata_5); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_get_bindata_6); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_get_data_type.h b/src/test/check_getdns_dict_get_data_type.h new file mode 100644 index 00000000..aaf55258 --- /dev/null +++ b/src/test/check_getdns_dict_get_data_type.h @@ -0,0 +1,231 @@ +#ifndef _check_getdns_dict_get_data_type_h_ +#define _check_getdns_dict_get_data_type_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ G E T _ D A T A _ T Y P E * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_get_data_type_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + getdns_data_type answer; + + ASSERT_RC(getdns_dict_get_data_type(this_dict, "key", &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_data_type()"); + + } + END_TEST + + START_TEST (getdns_dict_get_data_type_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + getdns_data_type answer; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_int(this_dict, "ten", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_data_type(this_dict, NULL, &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_data_type()"); + + DICT_DESTROY(this_dict); + + } + END_TEST + + START_TEST (getdns_dict_get_data_type_3) + { + /* + * name does not exist in dict + * Create a dict with three keys ("ten" = 10, "eleven" = 11, "twelve" = 12) + * Call getdns_dict_get_data_type() with name = "nine" + * expect: GETDNS_RETURN_NO_SUCH_DICT_NAME + */ + struct getdns_dict *this_dict = NULL; + char *keys[3] = { "ten", "eleven", "twelve" }; + uint32_t values[3] = { 10, 11, 12 }; + int i; + getdns_data_type answer; + + DICT_CREATE(this_dict); + + for(i = 0; i < 3; i++) + { + ASSERT_RC(getdns_dict_set_int(this_dict, keys[i], values[i]), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + } + + ASSERT_RC(getdns_dict_get_data_type(this_dict, "nine", &answer), + GETDNS_RETURN_NO_SUCH_DICT_NAME, "Return code from getdns_dict_get_names()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_data_type_4) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_int(this_dict, "ten", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_data_type(this_dict, "ten", NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_names()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_data_type_5) + { + /* + * data type is dict + * Create a dict + * Create a second dict and add it to the first as name = "dict" + * Call getdns_dict_get_data_type() for name = "dict" + * expect: GETDNS_RETURN_GOOD + * retrieved answer should = t_dict + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *second_dict = NULL; + getdns_data_type answer; + + DICT_CREATE(this_dict); + DICT_CREATE(second_dict); + ASSERT_RC(getdns_dict_set_dict(this_dict, "dict", second_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + ASSERT_RC(getdns_dict_get_data_type(this_dict, "dict", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_data_type()"); + + ck_assert_msg(answer == t_dict, "Expected answer = t_dict (%d), got: %d", t_dict, answer); + + DICT_DESTROY(this_dict); + DICT_DESTROY(second_dict); + } + END_TEST + + START_TEST (getdns_dict_get_data_type_6) + { + /* + * data type is list + * Create a dict + * Create a list and add it to the dict as name = "list" + * Call getdns_dict_get_data_type() for name = "list" + * expect: GETDNS_RETURN_GOOD + * retrieved answer should = t_list + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *list = NULL; + getdns_data_type answer; + + DICT_CREATE(this_dict); + LIST_CREATE(list); + ASSERT_RC(getdns_dict_set_list(this_dict, "list", list), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + ASSERT_RC(getdns_dict_get_data_type(this_dict, "list", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_data_type()"); + + ck_assert_msg(answer == t_list, "Expected answer = t_list (%d), got: %d", t_list, answer); + + DICT_DESTROY(this_dict); + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_dict_get_data_type_7) + { + /* + * data type is bindata + * Create a dict + * Create some bindata and add it to the dict as name = "bindata" + * Call getdns_dict_get_data_type() for name = "bindata" + * expect: GETDNS_RETURN_GOOD + * retrieved answer should = t_bindata + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + getdns_data_type answer; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_data_type(this_dict, "bindata", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_data_type()"); + + ck_assert_msg(answer == t_bindata, "Expected answer = t_bindata (%d), got: %d", t_bindata, answer); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_data_type_8) + { + /* + * data type is int + * Create a dict + * Add an int to the dict as name = "int" + * Call getdns_dict_get_data_type() for name = "int" + * expect: GETDNS_RETURN_GOOD + * retrieved answer should = t_int + */ + struct getdns_dict *this_dict = NULL; + getdns_data_type answer; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_int(this_dict, "int", 100), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_data_type(this_dict, "int", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_data_type()"); + + ck_assert_msg(answer == t_int, "Expected answer = t_int (%d), got: %d", t_int, answer); + + DICT_DESTROY(this_dict); + } + END_TEST + + Suite * + getdns_dict_get_data_type_suite (void) + { + Suite *s = suite_create ("getdns_dict_get_data_type()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_get_data_type_1); + tcase_add_test(tc_neg, getdns_dict_get_data_type_2); + tcase_add_test(tc_neg, getdns_dict_get_data_type_3); + tcase_add_test(tc_neg, getdns_dict_get_data_type_4); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_get_data_type_5); + tcase_add_test(tc_pos, getdns_dict_get_data_type_6); + tcase_add_test(tc_pos, getdns_dict_get_data_type_7); + tcase_add_test(tc_pos, getdns_dict_get_data_type_8); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_get_dict.h b/src/test/check_getdns_dict_get_dict.h new file mode 100644 index 00000000..99272d5b --- /dev/null +++ b/src/test/check_getdns_dict_get_dict.h @@ -0,0 +1,221 @@ +#ifndef _check_getdns_dict_get_dict_h_ +#define _check_getdns_dict_get_dict_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ G E T _ D I C T * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_get_dict_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *answer = NULL; + + ASSERT_RC(getdns_dict_get_dict(this_dict, "key", &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_dict()"); + + } + END_TEST + + START_TEST (getdns_dict_get_dict_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *second_dict = NULL; + struct getdns_dict *answer = NULL; + + DICT_CREATE(this_dict); + DICT_CREATE(second_dict); + ASSERT_RC(getdns_dict_set_dict(this_dict, "dict", second_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + ASSERT_RC(getdns_dict_get_dict(this_dict, NULL, &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_dict()"); + + DICT_DESTROY(this_dict); + DICT_DESTROY(second_dict); + } + END_TEST + + START_TEST (getdns_dict_get_dict_3) + { + /* + * name does not exist in dict + * Create a dict + * Create a second dict with three ints ("ten" = 10, "eleven" = 11, "twelve" = 12) + * Add the second dict to the first dict as name = "numbers" + * Call getdns_dict_get_dict() against the first dict with name = "letters" + * expect: GETDNS_RETURN_NO_SUCH_DICT_NAME + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *second_dict = NULL; + char *keys[3] = { "ten", "eleven", "twelve" }; + uint32_t values[3] = { 10, 11, 12 }; + int i; + struct getdns_dict *answer = NULL; + + DICT_CREATE(this_dict); + DICT_CREATE(second_dict); + + for(i = 0; i < 3; i++) + { + ASSERT_RC(getdns_dict_set_int(second_dict, keys[i], values[i]), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + } + + ASSERT_RC(getdns_dict_set_dict(this_dict, "numbers", second_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + ASSERT_RC(getdns_dict_get_dict(this_dict, "letters", &answer), + GETDNS_RETURN_NO_SUCH_DICT_NAME, "Return code from getdns_dict_get_dict()"); + + DICT_DESTROY(this_dict); + DICT_DESTROY(second_dict); + } + END_TEST + + START_TEST (getdns_dict_get_dict_4) + { + /* + * data type at name is not a dict + * Create a dict with one int (name = "ten", value = 10) + * Call getdns_dict_get_dict() with name = "ten" + * expect: GETDNS_RETURN_WRONG_TYPE_REQUESTED + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *answer = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, "ten", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_dict(this_dict, "ten", &answer), + GETDNS_RETURN_WRONG_TYPE_REQUESTED, "Return code from getdns_dict_get_dict()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_dict_5) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *second_dict = NULL; + + DICT_CREATE(this_dict); + DICT_CREATE(second_dict); + + ASSERT_RC(getdns_dict_set_dict(this_dict, "dict", second_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + ASSERT_RC(getdns_dict_get_dict(this_dict, "dict", NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_dict()"); + + DICT_DESTROY(this_dict); + DICT_DESTROY(second_dict); + } + END_TEST + + START_TEST (getdns_dict_get_dict_6) + { + /* + * successful get dict + * Create a dict + * Create a second dict with three ints ("ten" = 10, "eleven" = 11, "twelve" = 12) + * Add the second dict to the first dict as name = "numbers" + * Call getdns_dict_get_dict() against the first dict for name = "numbers" + * Call getdns_dict_get_names() against the retrieved "numbers" dict to get a list of names + * Call getdns_list_get_length() against the returned list to set a loop counter + * Iterate through the names in the list and add the int value from each key to sum + * expect: sum == 33 + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *second_dict = NULL; + char *keys[3] = { "ten", "eleven", "twelve" }; + uint32_t values[3] = { 10, 11, 12 }; + size_t i; + uint32_t sum_of_values = 0; + struct getdns_dict *answer = NULL; + struct getdns_list *names = NULL; + size_t length; + struct getdns_bindata *bindata = NULL; + uint32_t value; + uint32_t sum = 0; + + DICT_CREATE(this_dict); + DICT_CREATE(second_dict); + + for(i = 0; i < 3; i++) + { + ASSERT_RC(getdns_dict_set_int(second_dict, keys[i], values[i]), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + sum_of_values += values[i]; + } + + ASSERT_RC(getdns_dict_set_dict(this_dict, "numbers", second_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + ASSERT_RC(getdns_dict_get_dict(this_dict, "numbers", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_dict()"); + + ASSERT_RC(getdns_dict_get_names(answer, &names), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_names()"); + + ASSERT_RC(getdns_list_get_length(names, &length), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_length()"); + + for(i = 0; i < length; i++) + { + ASSERT_RC(getdns_list_get_bindata(names, i, &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_bindata()"); + ASSERT_RC(getdns_dict_get_int(answer, (char *)bindata->data, &value), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_int()"); + sum += value; + } + + ck_assert_msg(sum == sum_of_values, "Sum of int values in dict should == %d, got: %d", + sum_of_values, sum); + + LIST_DESTROY(names); + DICT_DESTROY(this_dict); + DICT_DESTROY(second_dict); + } + END_TEST + + Suite * + getdns_dict_get_dict_suite (void) + { + Suite *s = suite_create ("getdns_dict_get_dict()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_get_dict_1); + tcase_add_test(tc_neg, getdns_dict_get_dict_2); + tcase_add_test(tc_neg, getdns_dict_get_dict_3); + tcase_add_test(tc_neg, getdns_dict_get_dict_4); + tcase_add_test(tc_neg, getdns_dict_get_dict_5); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_get_dict_6); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_get_int.h b/src/test/check_getdns_dict_get_int.h new file mode 100644 index 00000000..994a210d --- /dev/null +++ b/src/test/check_getdns_dict_get_int.h @@ -0,0 +1,164 @@ +#ifndef _check_getdns_dict_get_int_h_ +#define _check_getdns_dict_get_int_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ G E T _ I N T * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_get_int_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + uint32_t answer; + + ASSERT_RC(getdns_dict_get_int(this_dict, "key", &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_int()"); + + } + END_TEST + + START_TEST (getdns_dict_get_int_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + uint32_t answer; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_int(this_dict, "int", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_int(this_dict, NULL, &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_int()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_int_3) + { + /* + * name does not exist in dict + * Create a dict with one int (name = "ten", value = 10) + * Call getdns_dict_get_int() against the dict with name = "nine" + * expect: GETDNS_RETURN_NO_SUCH_DICT_NAME + */ + struct getdns_dict *this_dict = NULL; + uint32_t answer; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_int(this_dict, "ten", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_int(this_dict, "nine", &answer), + GETDNS_RETURN_NO_SUCH_DICT_NAME, "Return code from getdns_dict_get_int()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_int_4) + { + /* + * data type at name is not int + * Create a dict + * Create some bindata containing "bindata" and add it to the dict with name = "bindata" + * Call getdns_dict_get_int() with name = "bindata" + * expect: GETDNS_RETURN_WRONG_TYPE_REQUESTED + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + uint32_t answer; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_int(this_dict, "bindata", &answer), + GETDNS_RETURN_WRONG_TYPE_REQUESTED, "Return code from getdns_dict_get_int()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_int_5) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, "int", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_int(this_dict, "int", NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_int()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_int_6) + { + /* + * successful get int + * Create a dict with one int (name = "ten", value = 10) + * Call getdns_dict_get_int() against the dict with name = "ten" + * expect: GETDNS_RETURN_GOOD + * int retrievedshould == 10 + * + */ + struct getdns_dict *this_dict = NULL; + uint32_t answer; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, "ten", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_int(this_dict, "ten", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_int()"); + + ck_assert_msg(answer == 10, "Expected retrieve int == 10, got: %d", + answer); + + DICT_DESTROY(this_dict); + } + END_TEST + + Suite * + getdns_dict_get_int_suite (void) + { + Suite *s = suite_create ("getdns_dict_get_int()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_get_int_1); + tcase_add_test(tc_neg, getdns_dict_get_int_2); + tcase_add_test(tc_neg, getdns_dict_get_int_3); + tcase_add_test(tc_neg, getdns_dict_get_int_4); + tcase_add_test(tc_neg, getdns_dict_get_int_5); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_get_int_6); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_get_list.h b/src/test/check_getdns_dict_get_list.h new file mode 100644 index 00000000..c5c370f0 --- /dev/null +++ b/src/test/check_getdns_dict_get_list.h @@ -0,0 +1,185 @@ +#ifndef _check_getdns_dict_get_list_h_ +#define _check_getdns_dict_get_list_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ G E T _ L I S T * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_get_list_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *answer = NULL; + + ASSERT_RC(getdns_dict_get_list(this_dict, "key", &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_list()"); + + } + END_TEST + + START_TEST (getdns_dict_get_list_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *list = NULL; + struct getdns_list *answer = NULL; + + DICT_CREATE(this_dict); + LIST_CREATE(list); + ASSERT_RC(getdns_dict_set_list(this_dict, "list", list), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + ASSERT_RC(getdns_dict_get_list(this_dict, NULL, &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_list()"); + + DICT_DESTROY(this_dict); + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_dict_get_list_3) + { + /* + * name does not exist in dict + * Create a dict with three ints ("ten" = 10, "eleven" = 11, "twelve" = 12) + * Call getdns_dict_get_list() against the first dict with name = "nine" + * expect: GETDNS_RETURN_NO_SUCH_DICT_NAME + */ + struct getdns_dict *this_dict = NULL; + char *keys[3] = { "ten", "eleven", "twelve" }; + uint32_t values[3] = { 10, 11, 12 }; + int i; + struct getdns_list *answer = NULL; + + DICT_CREATE(this_dict); + + for(i = 0; i < 3; i++) + { + ASSERT_RC(getdns_dict_set_int(this_dict, keys[i], values[i]), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + } + + ASSERT_RC(getdns_dict_get_list(this_dict, "nine", &answer), + GETDNS_RETURN_NO_SUCH_DICT_NAME, "Return code from getdns_dict_get_list()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_list_4) + { + /* + * data type at name is not a list + * Create a dict with one int (name = "ten", value = 10) + * Call getdns_dict_get_list() with name = "ten" + * expect: GETDNS_RETURN_WRONG_TYPE_REQUESTED + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *answer = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, "ten", 10), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_list(this_dict, "ten", &answer), + GETDNS_RETURN_WRONG_TYPE_REQUESTED, "Return code from getdns_dict_get_list()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_list_5) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *list = NULL; + + DICT_CREATE(this_dict); + LIST_CREATE(list); + + ASSERT_RC(getdns_dict_set_list(this_dict, "list", list), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + ASSERT_RC(getdns_dict_get_list(this_dict, "list", NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_list()"); + + DICT_DESTROY(this_dict); + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_dict_get_list_6) + { + /* + * successful get list + * Create a dict + * Create a list and set index 0 to an int with a value of 100 + * Add the list to the dict as name "list" + * Call getdns_dict_get_list() against the dict for name = "list" + * Call getdns_list_set_int() for index 0 + * expect: int retrieved = 100 + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *list = NULL; + struct getdns_list *answer = NULL; + uint32_t value; + + DICT_CREATE(this_dict); + LIST_CREATE(list); + + ASSERT_RC(getdns_list_set_int(list, 0, 100), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_int()"); + + ASSERT_RC(getdns_dict_set_list(this_dict, "list", list), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + ASSERT_RC(getdns_dict_get_list(this_dict, "list", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_list()"); + + ASSERT_RC(getdns_list_get_int(answer, 0, &value), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_int()"); + + ck_assert_msg(value == 100, "Expected int retrieved == 100, got: %d", value); + + DICT_DESTROY(this_dict); + LIST_DESTROY(list); + } + END_TEST + + Suite * + getdns_dict_get_list_suite (void) + { + Suite *s = suite_create ("getdns_dict_get_list()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_get_list_1); + tcase_add_test(tc_neg, getdns_dict_get_list_2); + tcase_add_test(tc_neg, getdns_dict_get_list_3); + tcase_add_test(tc_neg, getdns_dict_get_list_4); + tcase_add_test(tc_neg, getdns_dict_get_list_5); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_get_list_6); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_get_names.h b/src/test/check_getdns_dict_get_names.h new file mode 100644 index 00000000..6b7c0fcb --- /dev/null +++ b/src/test/check_getdns_dict_get_names.h @@ -0,0 +1,111 @@ +#ifndef _check_getdns_dict_get_names_h_ +#define _check_getdns_dict_get_names_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ G E T _ N A M E S * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_get_names_1) + { + /* + * this_dict = NULL + * expect = GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *answer = NULL; + + ASSERT_RC(getdns_dict_get_names(this_dict, &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_names()"); + + } + END_TEST + + START_TEST (getdns_dict_get_names_2) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_get_names(this_dict, NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_get_names()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_get_names_3) + { + /* + * Create a dict with three keys ("ten" = 10, "eleven" = 11, "twelve" = 12) + * Call getdns_dict_get_names() + * Iterate through list and append names together in a single string + * expect: string == "teneleventwelve" + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *answer = NULL; + char *keys[3] = { "ten", "eleven", "twelve" }; + uint32_t values[3] = { 10, 11, 12 }; + int i; + size_t length; + struct getdns_bindata *key = NULL; + char string_buffer[20] = ""; + + DICT_CREATE(this_dict); + + for(i = 0; i < 3; i++) + { + ASSERT_RC(getdns_dict_set_int(this_dict, keys[i], values[i]), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + } + + ASSERT_RC(getdns_dict_get_names(this_dict, &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_names()"); + + ASSERT_RC(getdns_list_get_length(answer, &length), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_length()"); + + ck_assert_msg(length == 3, "Expected length == 3, got %d", length); + + for(i = 0; i < length; i++) + { + ASSERT_RC(getdns_list_get_bindata(answer, i, &key), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_bindata()"); + strcat(string_buffer, (char *)key->data); + } + + ck_assert_msg(strcmp(string_buffer, "elevententwelve") == 0, + "Expected concatenated names to be \"elevententwelve\", got \"%s\"", string_buffer); + + LIST_DESTROY(answer); + DICT_DESTROY(this_dict); + } + END_TEST + + Suite * + getdns_dict_get_names_suite (void) + { + Suite *s = suite_create ("getdns_dict_get_names()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_get_names_1); + tcase_add_test(tc_neg, getdns_dict_get_names_2); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_get_names_3); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_set_bindata.h b/src/test/check_getdns_dict_set_bindata.h new file mode 100644 index 00000000..94da80b3 --- /dev/null +++ b/src/test/check_getdns_dict_set_bindata.h @@ -0,0 +1,160 @@ +#ifndef _check_getdns_dict_set_bindata_h_ +#define _check_getdns_dict_set_bindata_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ S E T _ B I N D A T A * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_set_bindata_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "key", &bindata), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_bindata()"); + + } + END_TEST + + START_TEST (getdns_dict_set_bindata_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, NULL, &bindata), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_bindata()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_set_bindata_3) + { + /* + * child_bindata = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_bindata()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_set_bindata_4) + { + /* + * name already exists in dict + * Create a dict + * Add bindata to the dict (name = "bindata", value = { 8, "bindata" }) + * Add bindata to the dict (name = "bindata", value = { 15, "second_bindata" }) + * Call getdns_dict_get_bindata() with name = "bindata" + * expect: GETDNS_RETURN_GOOD (all functions) + * bindata retrieved = "second_bindata" + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + struct getdns_bindata second_bindata = { 15, (void *)"second_bindata" }; + struct getdns_bindata *retrieved_bindata = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &second_bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_bindata(this_dict, "bindata", &retrieved_bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_bindata()"); + + ck_assert_msg(retrieved_bindata->size, second_bindata.size, + "Expected retrieved bindata size == %d, got: %d", + second_bindata.size, retrieved_bindata->size); + + ck_assert_msg(strcmp((char *)retrieved_bindata->data, (char *)second_bindata.data) == 0, + "Expected retrieved bindata to be \"%s\", got: \"%s\"", + (char *)second_bindata.data, (char *)retrieved_bindata->data); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_set_bindata_5) + { + /* + * name already exists in dict, changing data type + * Create a dict + * Add an int to the dict (name = "int", value = 100) + * Add bindata to the dict (name = "int", value = { 8, "bindata" }) + * Call getdns_dict_get_bindata() against the dict with name = "int" + * expect: GETDNS_RETURN_GOOD (all functions) + * retrieved bindata should == "bindata" + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + struct getdns_bindata *retrieved_bindata = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, "int", 100), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "int", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_get_bindata(this_dict, "int", &retrieved_bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_bindata()"); + + ck_assert_msg(retrieved_bindata->size == bindata.size, + "Expected retrieved bindata size == %d, got: %d", + bindata.size, retrieved_bindata->size); + + ck_assert_msg(strcmp((char *)retrieved_bindata->data, (char *)bindata.data) == 0, + "Expected bindata data to be \"%s\", got: \"%s\"", + (char *)bindata.data, (char *)retrieved_bindata->data); + + DICT_DESTROY(this_dict); + } + END_TEST + + Suite * + getdns_dict_set_bindata_suite (void) + { + Suite *s = suite_create ("getdns_dict_set_bindata()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_set_bindata_1); + tcase_add_test(tc_neg, getdns_dict_set_bindata_2); + tcase_add_test(tc_neg, getdns_dict_set_bindata_3); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_set_bindata_4); + tcase_add_test(tc_pos, getdns_dict_set_bindata_5); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_set_dict.h b/src/test/check_getdns_dict_set_dict.h new file mode 100644 index 00000000..0142fe0c --- /dev/null +++ b/src/test/check_getdns_dict_set_dict.h @@ -0,0 +1,187 @@ +#ifndef _check_getdns_dict_set_dict_h_ +#define _check_getdns_dict_set_dict_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ S E T _ D I C T * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_set_dict_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *child_dict = NULL; + + DICT_CREATE(child_dict); + ASSERT_RC(getdns_dict_set_dict(this_dict, "dict", child_dict), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_dict()"); + DICT_DESTROY(child_dict); + + } + END_TEST + + START_TEST (getdns_dict_set_dict_2) + { + /* + * name= NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *child_dict = NULL; + + DICT_CREATE(this_dict); + DICT_CREATE(child_dict); + ASSERT_RC(getdns_dict_set_dict(this_dict, NULL, child_dict), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_dict()"); + + DICT_DESTROY(this_dict); + DICT_DESTROY(child_dict); + + } + END_TEST + + START_TEST (getdns_dict_set_dict_3) + { + /* + * child_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_dict *child_dict = NULL; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_dict(this_dict, "dict", child_dict), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_dict()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_set_dict_4) + { + /* + * name already exists in dict + * Create a dict + * Create a second dict containing name = "int" with value = 100 + * Add the second dict to the first dict as name = "dict" + * Create a third dict containing name = "int" with value = 101 + * Add the third dict to the first dict as name = "dict" + * Call getdns_dict_get_dict() against the first dict with name = "dict" + * Call getdns_dict_get_int() against the retrieved dict for name = "int" + * expect: GETDNS_RETURN_GOOD (all functions) + * retrieved int should = 101 + */ + struct getdns_dict *first_dict = NULL; + struct getdns_dict *second_dict = NULL; + struct getdns_dict *third_dict = NULL; + struct getdns_dict *answer = NULL; + uint32_t retrieved_int; + + DICT_CREATE(first_dict); + + DICT_CREATE(second_dict); + ASSERT_RC(getdns_dict_set_int(second_dict, "int", 100), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + ASSERT_RC(getdns_dict_set_dict(first_dict, "dict", second_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + DICT_CREATE(third_dict); + ASSERT_RC(getdns_dict_set_int(third_dict, "int", 101), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + ASSERT_RC(getdns_dict_set_dict(first_dict, "dict", third_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + ASSERT_RC(getdns_dict_get_dict(first_dict, "dict", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_dict()"); + + ASSERT_RC(getdns_dict_get_int(answer, "int", &retrieved_int), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_int()"); + + ck_assert_msg(retrieved_int == 101, "Exepected retrieved int == 101, got: %d", + retrieved_int); + + DICT_DESTROY(first_dict); + DICT_DESTROY(second_dict); + DICT_DESTROY(third_dict); + } + END_TEST + + START_TEST (getdns_dict_set_dict_5) + { + /* + * name already exists in dict, changing data type + * Create a dict + * Create a list + * Set list value at index 0 to int 100 + * Add the list to the dict as name = "list" + * Create a second dict + * Add an int to the second dict with name = "int", value = 101 + * Add the second dict to the first dict as name = "list" + * Call getdns_dict_get_dict to retrieve the second dict + * Call getdns_dict_get_int with name = "int" + * expect: GETDNS_RETURN_GOOD (all functions) + * retrieved int should = 101 + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *list = NULL; + struct getdns_dict *second_dict = NULL; + struct getdns_dict *answer = NULL; + uint32_t retrieved_int; + + DICT_CREATE(this_dict); + + LIST_CREATE(list); + ASSERT_RC(getdns_list_set_int(list, 0, 100), + GETDNS_RETURN_GOOD, "Return code from getdns_list_set_int()"); + + ASSERT_RC(getdns_dict_set_list(this_dict, "list", list), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_list()"); + + DICT_CREATE(second_dict); + ASSERT_RC(getdns_dict_set_int(second_dict, "int", 101), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + ASSERT_RC(getdns_dict_set_dict(this_dict, "list", second_dict), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_dict()"); + + ASSERT_RC(getdns_dict_get_dict(this_dict, "list", &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_dict()"); + ASSERT_RC(getdns_dict_get_int(answer, "int", &retrieved_int), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_int()"); + + ck_assert_msg(retrieved_int == 101, "Exepected retrieved int == 101, got: %d", + retrieved_int); + + DICT_DESTROY(this_dict); + LIST_DESTROY(list); + DICT_DESTROY(second_dict); + } + END_TEST + + Suite * + getdns_dict_set_dict_suite (void) + { + Suite *s = suite_create ("getdns_dict_set_dict()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_set_dict_1); + tcase_add_test(tc_neg, getdns_dict_set_dict_2); + tcase_add_test(tc_neg, getdns_dict_set_dict_3); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_set_dict_4); + tcase_add_test(tc_pos, getdns_dict_set_dict_5); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_set_int.h b/src/test/check_getdns_dict_set_int.h new file mode 100644 index 00000000..1310e4de --- /dev/null +++ b/src/test/check_getdns_dict_set_int.h @@ -0,0 +1,128 @@ +#ifndef _check_getdns_dict_set_int_h_ +#define _check_getdns_dict_set_int_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ S E T _ I N T * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_set_int_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + + ASSERT_RC(getdns_dict_set_int(this_dict, "key", 100), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_int()"); + + } + END_TEST + + START_TEST (getdns_dict_set_int_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, NULL, 100), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_int()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_set_int_3) + { + /* + * name already exists in dict + * Create a dict + * Add an int to the dict (name = "int", value = 100) + * Add an int to the dict (name = "int", value = 101) + * Call getdns_dict_get_int() against the dict with name = "int" + * expect: GETDNS_RETURN_GOOD (all functions) + * int retrieved should = 101 + */ + struct getdns_dict *this_dict = NULL; + uint32_t value; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_int(this_dict, "int", 100), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_set_int(this_dict, "int", 101), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_int(this_dict, "int", &value), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_int()"); + + ck_assert_msg(value == 101, "Expected retrieved int == 101, got: %d", + value); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_set_int_4) + { + /* + * name already exists in dict, changing data type + * Create a dict + * Add bindata to the dict (name = "bindata", value = { 8, "bindata" }) + * Add an int to the dict (name = "bindata", value = 101) + * Call getdns_dict_get_int() with name = "bindata" + * expect: GETDNS_RETURN_GOOD (all functions) + * int retrieved should = 101 + */ + struct getdns_dict *this_dict = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + uint32_t value; + + DICT_CREATE(this_dict); + + ASSERT_RC(getdns_dict_set_bindata(this_dict, "bindata", &bindata), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_bindata()"); + + ASSERT_RC(getdns_dict_set_int(this_dict, "bindata", 101), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_get_int(this_dict, "bindata", &value), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_int()"); + + ck_assert_msg(value == 101, "Expected retrieved int == 101, got: %d", + value); + + DICT_DESTROY(this_dict); + } + END_TEST + + Suite * + getdns_dict_set_int_suite (void) + { + Suite *s = suite_create ("getdns_dict_set_int()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_set_int_1); + tcase_add_test(tc_neg, getdns_dict_set_int_2); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_set_int_3); + tcase_add_test(tc_pos, getdns_dict_set_int_4); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_dict_set_list.h b/src/test/check_getdns_dict_set_list.h new file mode 100644 index 00000000..a17c0983 --- /dev/null +++ b/src/test/check_getdns_dict_set_list.h @@ -0,0 +1,190 @@ +#ifndef _check_getdns_dict_set_list_h_ +#define _check_getdns_dict_set_list_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ D I C T _ S E T _ L I S T * + * * + ************************************************************************** + */ + + START_TEST (getdns_dict_set_list_1) + { + /* + * this_dict = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *list = NULL; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_list(this_dict, "list", list), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_list()"); + + } + END_TEST + + START_TEST (getdns_dict_set_list_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *list = NULL; + + DICT_CREATE(this_dict); + LIST_CREATE(list); + ASSERT_RC(getdns_dict_set_list(this_dict, NULL, list), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_list()"); + + DICT_DESTROY(this_dict); + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_dict_set_list_3) + { + /* + * child_list = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_dict *this_dict = NULL; + + DICT_CREATE(this_dict); + ASSERT_RC(getdns_dict_set_list(this_dict, "list", NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_dict_set_list()"); + + DICT_DESTROY(this_dict); + } + END_TEST + + START_TEST (getdns_dict_set_list_4) + { + /* + * name already exists in dict + * Create a dict + * Create a list + * Set list value at index 0 via getdns_list_set_int() to 100 + * Add the list to the dict as name "list" + * Create a second list + * Set list value at index 0 in the second list to 101 + * Add the second list to the dict using name "list" again + * Call getdns_dict_get_list() against the dict with name = "list" + * Call getdns_list_get_int() for index 0 against the retrieved list + * expect: GETDNS_RETURN_GOOD (all functions) + * retrieved int should = 101 + */ + struct getdns_dict *this_dict = NULL; + struct getdns_list *first_list = NULL; + struct getdns_list *second_list = NULL; + struct getdns_list *retrieved_list = NULL; + uint32_t value; + + DICT_CREATE(this_dict); + + LIST_CREATE(first_list); + ASSERT_RC(getdns_list_set_int(first_list, 0, 100), + GETDNS_RETURN_GOOD, "Return from getdns_list_set_int()"); + + ASSERT_RC(getdns_dict_set_list(this_dict, "list", first_list), + GETDNS_RETURN_GOOD, "Return from getdns_list_set_list()"); + + LIST_CREATE(second_list); + ASSERT_RC(getdns_list_set_int(second_list, 0, 101), + GETDNS_RETURN_GOOD, "Return from getdns_list_set_int()"); + + ASSERT_RC(getdns_dict_set_list(this_dict, "list", second_list), + GETDNS_RETURN_GOOD, "Return from getdns_list_set_list()"); + + ASSERT_RC(getdns_dict_get_list(this_dict, "list", &retrieved_list), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_list()"); + + ASSERT_RC(getdns_list_get_int(retrieved_list, 0, &value), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_int()"); + + ck_assert_msg(value == 101, "Expected int retrieved == 101, got: %d", + value); + + DICT_DESTROY(this_dict); + LIST_DESTROY(first_list); + LIST_DESTROY(second_list); + } + END_TEST + + START_TEST (getdns_dict_set_list_5) + { + /* + * name already exists in dict, changing data type + * Create a dict + * Create a second dict + * Add an int to the second dict (name = "int", value = 100) + * Add the second dict to the first dict as name "list" + * Create a list + * Set list value at index 0 in the list to 101 + * Add the list to the first dict using name "list" again + * Call getdns_dict_get_list() against the dict with name = "list" + * Call getdns_list_get_int() for index 0 against the retrieved list + * expect: GETDNS_RETURN_GOOD (all functions) + * retrieved int should = 101 + */ + struct getdns_dict *first_dict = NULL; + struct getdns_dict *second_dict = NULL; + struct getdns_list *list = NULL; + struct getdns_list *retrieved_list = NULL; + uint32_t value; + + DICT_CREATE(first_dict); + + DICT_CREATE(second_dict); + ASSERT_RC(getdns_dict_set_int(second_dict, "int", 100), + GETDNS_RETURN_GOOD, "Return from getdns_dict_set_int()"); + + ASSERT_RC(getdns_dict_set_dict(first_dict, "list", second_dict), + GETDNS_RETURN_GOOD, "Return from getdns_dict_set_dict()"); + + LIST_CREATE(list); + ASSERT_RC(getdns_list_set_int(list, 0, 101), + GETDNS_RETURN_GOOD, "Return from getdns_list_set_int()"); + + ASSERT_RC(getdns_dict_set_list(first_dict, "list", list), + GETDNS_RETURN_GOOD, "Return from getdns_dict_set_list()"); + + ASSERT_RC(getdns_dict_get_list(first_dict, "list", &retrieved_list), + GETDNS_RETURN_GOOD, "Return code from getdns_dict_get_list()"); + + ASSERT_RC(getdns_list_get_int(retrieved_list, 0, &value), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_int()"); + + ck_assert_msg(value == 101, "Expected int retrieved == 101, got: %d", + value); + + DICT_DESTROY(first_dict); + DICT_DESTROY(second_dict); + LIST_DESTROY(list); + } + END_TEST + + Suite * + getdns_dict_set_list_suite (void) + { + Suite *s = suite_create ("getdns_dict_set_list()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_dict_set_list_1); + tcase_add_test(tc_neg, getdns_dict_set_list_2); + tcase_add_test(tc_neg, getdns_dict_set_list_3); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_dict_set_list_4); + tcase_add_test(tc_pos, getdns_dict_set_list_5); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_general.h b/src/test/check_getdns_general.h new file mode 100644 index 00000000..4fa2c1d9 --- /dev/null +++ b/src/test/check_getdns_general.h @@ -0,0 +1,453 @@ +#ifndef _check_getdns_general_h_ +#define _check_getdns_general_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ G E M E R A L * + * * + ************************************************************************** + */ + + START_TEST (getdns_general_1) + { + /* + * context = NULL + * expect: GETDNS_RETURN_BAD_CONTEXT + */ + struct getdns_context *context = NULL; + getdns_transaction_t transaction_id = 0; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + NULL, &transaction_id, callbackfn), + GETDNS_RETURN_BAD_CONTEXT, "Return code from getdns_general()"); + } + END_TEST + + START_TEST (getdns_general_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, NULL, GETDNS_RRTYPE_A, NULL, + NULL, &transaction_id, callbackfn), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_3) + { + /* + * name = invalid domain (too many octets) + * expect: GETDNS_RETURN_BAD_DOMAIN_NAME + */ + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + const char *name = "oh.my.gosh.and.for.petes.sake.are.you.fricking.crazy.man.because.this.spectacular.and.elaborately.thought.out.domain.name.of.very.significant.length.is.just.too.darn.long.because.you.know.the rfc.states.that.two.hundred.fifty.five.characters.is.the.max.com"; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, name, GETDNS_RRTYPE_A, NULL, + NULL, &transaction_id, callbackfn), + GETDNS_RETURN_BAD_DOMAIN_NAME, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_4) + { + /* + * name = invalid domain (label too long) + * expect: GETDNS_RETURN_BAD_DOMAIN_NAME + */ + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + const char *name = "this.domain.hasalabelwhichexceedsthemaximumdnslabelsizeofsixtythreecharacters.com"; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, name, GETDNS_RRTYPE_A, NULL, + NULL, &transaction_id, callbackfn), + GETDNS_RETURN_BAD_DOMAIN_NAME, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_5) + { + /* + * callbackfn = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + NULL, &transaction_id, NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_6) + { + /* + * name = "google.com" + * request_type = 0 (minimum valid RRTYPE) + * expect: NOERROR/NODATA response: + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount = 0 (number of records in ANSWER section) + */ + void verify_getdns_general_6(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", 0, NULL, + verify_getdns_general_6, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_6(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_nodata(ex_response); + } + + START_TEST (getdns_general_7) + { + /* + * name = "google.com" + * request_type = 65279 (maximum unassigned RRTYPE) + * expect: NOERROR/NODATA response: + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount = 0 (number of records in ANSWER section) + */ + void verify_getdns_general_7(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", 65279, NULL, + verify_getdns_general_7, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_7(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_nodata(ex_response); + } + + START_TEST (getdns_general_8) + { + /* + * name = "google.com" + * request_type = GETDNS_RRTYPE_A + * expect: NOERROR response with A records + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and equals number of A records ("type": 1) in "answer" list + */ + void verify_getdns_general_8(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + verify_getdns_general_8, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_8(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_address_in_answer(ex_response, TRUE, FALSE); + } + + START_TEST (getdns_general_9) + { + /* + * name = "google.com" + * request_type = GETDNS_RRTYPE_AAAA + * expect: NOERROR response with AAAA records + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and equals number of AAAA records ("type": 28) in "answer" list + */ + void verify_getdns_general_9(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_AAAA, NULL, + verify_getdns_general_9, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_9(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_address_in_answer(ex_response, FALSE, TRUE); + } + + START_TEST (getdns_general_10) + { + /* + * name = "thisdomainsurelydoesntexist.com" + * request_type = GETDNS_RRTYPE_TXT` + * expect: NXDOMAIN response with SOA record + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 3 + * ancount = 0 (number of records in ANSWER section) + * nscount = 1 (number of records in AUTHORITY section) + * and SOA record ("type": 6) present in "authority" list + */ + void verify_getdns_general_10(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + const char *name = "thisdomainsurelydoesntexist.com"; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, name, GETDNS_RRTYPE_TXT, NULL, + verify_getdns_general_10, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_10(struct extracted_response *ex_response) + { + assert_nxdomain(ex_response); + assert_nodata(ex_response); + assert_soa_in_authority(ex_response); + } + + START_TEST (getdns_general_11) + { + /* + * name = "hampster.com" need to replace this with domain from unbound zone + * request_type = GETDNS_RRTYPE_MX + * expect: NOERROR/NODATA response: + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount = 0 (number of records in ANSWER section) + */ + void verify_getdns_general_11(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "hampster.com", GETDNS_RRTYPE_MX, NULL, + verify_getdns_general_11, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_11(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_nodata(ex_response); + } + + START_TEST (getdns_general_12) + { + /* + * name = "google.com" need to swap this out for max domain name length with max lable length` + * request_type = GETDNS_RRTYPE_A + * expect: NOERROR response with A records + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and equals number of A records ("type": 1) in "answer" list + */ + void verify_getdns_general_12(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "google.com", GETDNS_RRTYPE_A, NULL, + verify_getdns_general_12, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_12(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_address_in_answer(ex_response, TRUE, FALSE); + } + + START_TEST (getdns_general_13) + { + /* + * name = "75.101.146.66" need to change this to local unbound data + * request_type = GETDNS_RRTYPE_PTR + * expect: NOERROR response with PTR record + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount == 1 (number of records in ANSWER section) + * and PTR record found ("type": 12) in "answer" list + */ + void verify_getdns_general_13(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "75.101.146.66", GETDNS_RRTYPE_PTR, NULL, + verify_getdns_general_13, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_13(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_ptr_in_answer(ex_response); + } + + START_TEST (getdns_general_14) + { + /* + * name = "2607:f8b0:4006:802::1007" need to change this to local unbound data + * request_type = GETDNS_RRTYPE_PTR + * expect: NOERROR response with PTR record + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount == 1 (number of records in ANSWER section) + * and PTR record found ("type": 12) in "answer" list + */ + void verify_getdns_general_14(struct extracted_response *ex_response); + struct getdns_context *context = NULL; \ + struct event_base *event_base = NULL; \ + getdns_transaction_t transaction_id = 0; + + CONTEXT_CREATE(TRUE); + EVENT_BASE_CREATE; + + ASSERT_RC(getdns_general(context, "2607:f8b0:4006:802::1007", GETDNS_RRTYPE_PTR, NULL, + verify_getdns_general_14, &transaction_id, callbackfn), + GETDNS_RETURN_GOOD, "Return code from getdns_general()"); + + RUN_EVENT_LOOP; + CONTEXT_DESTROY; + } + END_TEST + + void verify_getdns_general_14(struct extracted_response *ex_response) + { + assert_noerror(ex_response); + assert_ptr_in_answer(ex_response); + } + + Suite * + getdns_general_suite (void) + { + Suite *s = suite_create ("getdns_general()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_general_1); + tcase_add_test(tc_neg, getdns_general_2); + tcase_add_test(tc_neg, getdns_general_3); + tcase_add_test(tc_neg, getdns_general_4); + tcase_add_test(tc_neg, getdns_general_5); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_general_6); + tcase_add_test(tc_pos, getdns_general_7); + tcase_add_test(tc_pos, getdns_general_8); + tcase_add_test(tc_pos, getdns_general_9); + tcase_add_test(tc_pos, getdns_general_10); + tcase_add_test(tc_pos, getdns_general_11); + tcase_add_test(tc_pos, getdns_general_12); + tcase_add_test(tc_pos, getdns_general_13); + tcase_add_test(tc_pos, getdns_general_14); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_general_sync.h b/src/test/check_getdns_general_sync.h new file mode 100644 index 00000000..f56df85e --- /dev/null +++ b/src/test/check_getdns_general_sync.h @@ -0,0 +1,381 @@ +#ifndef _check_getdns_general_sync_h_ +#define _check_getdns_general_sync_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ G E N E R A L _ S Y N C * + * * + ************************************************************************** + */ + + START_TEST (getdns_general_sync_1) + { + /* + * context = NULL + * expect: GETDNS_RETURN_BAD_CONTEXT + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + ASSERT_RC(getdns_general_sync(context, "google.com", GETDNS_RRTYPE_A, NULL, &response), + GETDNS_RETURN_BAD_CONTEXT, "Return code from getdns_general_sync()"); + } + END_TEST + + START_TEST (getdns_general_sync_2) + { + /* + * name = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, NULL, GETDNS_RRTYPE_A, NULL, &response), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_general_sync()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_3) + { + /* + * name = invalid domain (too many octets) + * expect: GETDNS_RETURN_BAD_DOMAIN_NAME + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + const char *name = "oh.my.gosh.and.for.petes.sake.are.you.fricking.crazy.man.because.this.spectacular.and.elaborately.thought.out.domain.name.of.very.significant.length.is.just.too.darn.long.because.you.know.the rfc.states.that.two.hundred.fifty.five.characters.is.the.max.com"; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, name, GETDNS_RRTYPE_A, NULL, &response), + GETDNS_RETURN_BAD_DOMAIN_NAME, "Return code from getdns_general_sync()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_4) + { + /* + * name = invalid domain (label too long) + * expect: GETDNS_RETURN_BAD_DOMAIN_NAME + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + const char *name = "this.domain.hasalabelwhichexceedsthemaximumdnslabelsizeofsixtythreecharacters.com"; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, name, GETDNS_RRTYPE_A, NULL, &response), + GETDNS_RETURN_BAD_DOMAIN_NAME, "Return code from getdns_general_sync()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_5) + { + /* + * response = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_context *context = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "google.com", GETDNS_RRTYPE_A, NULL, NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_general_sync()"); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_6) + { + /* + * name = "google.com" + * request_type = 0 (minimum valid RRTYPE) + * expect: NOERROR/NODATA response: + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount = 0 (number of records in ANSWER section) + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "google.com", 0, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_nodata(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_7) + { + /* + * name = "google.com" + * request_type = 65279 (maximum unassigned RRTYPE) + * expect: NOERROR/NODATA response: + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount = 0 (number of records in ANSWER section) + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "google.com", 65279, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_nodata(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_8) + { + /* + * name = "google.com" + * request_type = GETDNS_RRTYPE_A + * expect: NOERROR response with A records + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and equals number of A records ("type": 1) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "google.com", GETDNS_RRTYPE_A, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_address_in_answer(&ex_response, TRUE, FALSE); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_9) + { + /* + * name = "google.com" + * request_type = GETDNS_RRTYPE_AAAA + * expect: NOERROR response with AAAA records + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and equals number of AAAA records ("type": 28) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "google.com", GETDNS_RRTYPE_AAAA, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_address_in_answer(&ex_response, FALSE, TRUE); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_10) + { + /* + * name = "thisdomainsurelydoesntexist.com" + * request_type = GETDNS_RRTYPE_TXT` + * expect: NXDOMAIN response with SOA record + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 3 + * ancount = 0 (number of records in ANSWER section) + * nscount = 1 (number of records in AUTHORITY section) + * and SOA record ("type": 6) present in "authority" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + const char *name = "thisdomainsurelydoesntexist.com"; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, name, GETDNS_RRTYPE_TXT, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_nxdomain(&ex_response); + assert_nodata(&ex_response); + assert_soa_in_authority(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_11) + { + /* + * name = "hampster.com" need to replace this with domain from unbound zone + * request_type = GETDNS_RRTYPE_MX + * expect: NOERROR/NODATA response: + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount = 0 (number of records in ANSWER section) + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "hampster.com", GETDNS_RRTYPE_MX, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_nodata(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_12) + { + /* + * name = "google.com" need to swap this out for max domain name length with max lable length` + * request_type = GETDNS_RRTYPE_A + * expect: NOERROR response with A records + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount >= 1 (number of records in ANSWER section) + * and equals number of A records ("type": 1) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "google.com", GETDNS_RRTYPE_A, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_address_in_answer(&ex_response, TRUE, FALSE); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_13) + { + /* + * name = "75.101.146.66" need to change this to local unbound data + * request_type = GETDNS_RRTYPE_PTR + * expect: NOERROR response with PTR record + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount == 1 (number of records in ANSWER section) + * and PTR record found ("type": 12) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "75.101.146.66", GETDNS_RRTYPE_PTR, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_ptr_in_answer(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + START_TEST (getdns_general_sync_14) + { + /* + * name = "2607:f8b0:4006:802::1007" need to change this to local unbound data + * request_type = GETDNS_RRTYPE_PTR + * expect: NOERROR response with PTR record + * status = GETDNS_RESPSTATUS_GOOD + * rcode = 0 + * ancount == 1 (number of records in ANSWER section) + * and PTR record found ("type": 12) in "answer" list + */ + struct getdns_context *context = NULL; + struct getdns_dict *response = NULL; + + CONTEXT_CREATE(TRUE); + + ASSERT_RC(getdns_general_sync(context, "2607:f8b0:4006:802::1007", GETDNS_RRTYPE_PTR, NULL, &response), + GETDNS_RETURN_GOOD, "Return code from getdns_general_sync()"); + + EXTRACT_RESPONSE; + + assert_noerror(&ex_response); + assert_ptr_in_answer(&ex_response); + + CONTEXT_DESTROY; + } + END_TEST + + Suite * + getdns_general_sync_suite (void) + { + Suite *s = suite_create ("getdns_general_sync()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_general_sync_1); + tcase_add_test(tc_neg, getdns_general_sync_2); + tcase_add_test(tc_neg, getdns_general_sync_3); + tcase_add_test(tc_neg, getdns_general_sync_4); + tcase_add_test(tc_neg, getdns_general_sync_5); + suite_add_tcase(s, tc_neg); + /* Positive test cases */ + + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_general_sync_6); + tcase_add_test(tc_pos, getdns_general_sync_7); + tcase_add_test(tc_pos, getdns_general_sync_8); + tcase_add_test(tc_pos, getdns_general_sync_9); + tcase_add_test(tc_pos, getdns_general_sync_10); + tcase_add_test(tc_pos, getdns_general_sync_11); + tcase_add_test(tc_pos, getdns_general_sync_12); + tcase_add_test(tc_pos, getdns_general_sync_13); + tcase_add_test(tc_pos, getdns_general_sync_14); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_libevent.h b/src/test/check_getdns_libevent.h new file mode 100644 index 00000000..3dbcaf75 --- /dev/null +++ b/src/test/check_getdns_libevent.h @@ -0,0 +1,5 @@ +#ifdef HAVE_EVENT2_EVENT_H +#include +#else +#include +#endif diff --git a/src/test/check_getdns_list_get_data_type.h b/src/test/check_getdns_list_get_data_type.h new file mode 100644 index 00000000..eb968533 --- /dev/null +++ b/src/test/check_getdns_list_get_data_type.h @@ -0,0 +1,235 @@ +#ifndef _check_getdns_list_get_data_type_h_ +#define _check_getdns_list_get_data_type_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ L I S T _ G E T _ D A T A _ T Y P E * + * * + ************************************************************************** + */ + + START_TEST (getdns_list_get_data_type_1) + { + /* + * list = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_list *list = NULL; + size_t index = 0; + getdns_data_type answer; + + ASSERT_RC(getdns_list_get_data_type(list, index, &answer), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_list_get_data_type()"); + } + END_TEST + + START_TEST (getdns_list_get_data_type_2) + { + /* + * index is out of range + * Create a list, add an int to it, and then attempt + * to get the data type at index 1 + * expect: GETDNS_RETURN_NO_SUCH_LIST_ITEM + */ + struct getdns_list *list = NULL; + size_t index = 0; + getdns_data_type answer; + + LIST_CREATE(list); + + ASSERT_RC(getdns_list_set_int(list, index, 1), GETDNS_RETURN_GOOD, + "Return code from getdns_list_set_int()"); + + index++; + ASSERT_RC(getdns_list_get_data_type(list, index, &answer), + GETDNS_RETURN_NO_SUCH_LIST_ITEM, "Return code from getdns_list_get_data_type()"); + + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_list_get_data_type_3) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_list *list = NULL; + size_t index = 0; + + LIST_CREATE(list); + + ASSERT_RC(getdns_list_set_int(list, index, 1), GETDNS_RETURN_GOOD, + "Return code from getdns_list_set_int()"); + + ASSERT_RC(getdns_list_get_data_type(list, index, NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_list_get_data_type()"); + + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_list_get_data_type_4) + { + /* + * Create a list (empty) and attempt to get the + * data type at index 0. + * expect: GETDNS_RETURN_NO_SUCH_LIST_ITEM + */ + struct getdns_list *list = NULL; + size_t index = 0; + getdns_data_type answer; + + LIST_CREATE(list); + + ASSERT_RC(getdns_list_get_data_type(list, index, &answer), + GETDNS_RETURN_NO_SUCH_LIST_ITEM, "Return code from getdns_list_get_data_type()"); + + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_list_get_data_type_5) + { + /* + * Create a list, create a dict, set list value at index 0 + * to the dict, and then get the data type at index 0. + * data type at index 0. + * expect: GETDNS_RETURN_GOOD + * answer = t_dict (retrieved data type) + */ + struct getdns_list *list = NULL; + struct getdns_dict *dict = NULL; + size_t index = 0; + getdns_data_type answer; + + LIST_CREATE(list); + DICT_CREATE(dict); + + ASSERT_RC(getdns_list_set_dict(list, index, dict), GETDNS_RETURN_GOOD, + "Return code from getdns_list_set_dict()"); + + ASSERT_RC(getdns_list_get_data_type(list, index, &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_data_type()"); + + ck_assert_msg(answer == t_dict, + "Wrong data type, expected t_dict: %d, got %d", t_dict, answer); + + LIST_DESTROY(list); + DICT_DESTROY(dict); + } + END_TEST + + START_TEST (getdns_list_get_data_type_6) + { + /* + * Create a list, create a second list, set list value at + * index 0 to the second list, and then get the data type + * at index 0. + * expect: GETDNS_RETURN_GOOD + * answer = t_list (retrieved data type) + */ + struct getdns_list *list1 = NULL; + struct getdns_list *list2 = NULL; + size_t index = 0; + getdns_data_type answer; + + LIST_CREATE(list1); + LIST_CREATE(list2); + + ASSERT_RC(getdns_list_set_list(list1, index, list2), GETDNS_RETURN_GOOD, + "Return code from getdns_list_set_list()"); + + ASSERT_RC(getdns_list_get_data_type(list1, index, &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_data_type()"); + + ck_assert_msg(answer == t_list, + "Wrong data type, expected t_list: %d, got %d", t_list, answer); + + LIST_DESTROY(list1); + LIST_DESTROY(list2); + } + END_TEST + + START_TEST (getdns_list_get_data_type_7) + { + /* + * Create a list, create some bindata, set list value at + * index 0 to the bindata, and then get the data type at + * index 0. + * expect: GETDNS_RETURN_GOOD + * answer = t_bindata (retrieved data type) + */ + struct getdns_list *list = NULL; + struct getdns_bindata bindata = { 8, (void *)"bindata" }; + size_t index = 0; + getdns_data_type answer; + + LIST_CREATE(list); + + ASSERT_RC(getdns_list_set_bindata(list, index, &bindata), GETDNS_RETURN_GOOD, + "Return code from getdns_list_set_bindata()"); + + ASSERT_RC(getdns_list_get_data_type(list, index, &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_data_type()"); + + ck_assert_msg(answer == t_bindata, + "Wrong data type, expected t_bindata: %d, got %d", t_bindata, answer); + + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_list_get_data_type_8) + { + /* + * Create a list, set list value at index 0 to 100 (int), + * and then get the data type at index 0. + * expect: GETDNS_RETURN_GOOD + * answer = t_int (retrieved data type) + */ + struct getdns_list *list = NULL; + size_t index = 0; + getdns_data_type answer; + + LIST_CREATE(list); + + ASSERT_RC(getdns_list_set_int(list, index, 100), GETDNS_RETURN_GOOD, + "Return code from getdns_list_set_int()"); + + ASSERT_RC(getdns_list_get_data_type(list, index, &answer), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_data_type()"); + + ck_assert_msg(answer == t_int, + "Wrong data type, expected t_int: %d, got %d", t_int, answer); + + LIST_DESTROY(list); + } + END_TEST + + Suite * + getdns_list_get_data_type_suite (void) + { + Suite *s = suite_create ("getdns_list_get_data_type()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_list_get_data_type_1); + tcase_add_test(tc_neg, getdns_list_get_data_type_2); + tcase_add_test(tc_neg, getdns_list_get_data_type_3); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_list_get_data_type_4); + tcase_add_test(tc_pos, getdns_list_get_data_type_5); + tcase_add_test(tc_pos, getdns_list_get_data_type_6); + tcase_add_test(tc_pos, getdns_list_get_data_type_7); + tcase_add_test(tc_pos, getdns_list_get_data_type_8); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif diff --git a/src/test/check_getdns_list_get_length.h b/src/test/check_getdns_list_get_length.h new file mode 100644 index 00000000..9c71c2c4 --- /dev/null +++ b/src/test/check_getdns_list_get_length.h @@ -0,0 +1,113 @@ +#ifndef _check_getdns_list_get_length_h_ +#define _check_getdns_list_get_length_h_ + + /* + ************************************************************************** + * * + * T E S T S F O R G E T D N S _ L I S T _ G E T _ L E N G T H * + * * + ************************************************************************** + */ + + START_TEST (getdns_list_get_length_1) + { + /* + * list = NULL + * expect = GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_list *list = NULL; + size_t length; + + ASSERT_RC(getdns_list_get_length(list, &length), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_list_get_length()"); + + } + END_TEST + + START_TEST (getdns_list_get_length_2) + { + /* + * answer = NULL + * expect: GETDNS_RETURN_INVALID_PARAMETER + */ + struct getdns_list *list = NULL; + + LIST_CREATE(list); + + ASSERT_RC(getdns_list_get_length(list, NULL), + GETDNS_RETURN_INVALID_PARAMETER, "Return code from getdns_list_get_length()"); + + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_list_get_length_3) + { + /* + * Create a list, add 3 ints to it, get the length. + * expect: GETDNS_RETURN_GOOD + * length = 3 + */ + struct getdns_list *list = NULL; + size_t i; + size_t length; + + LIST_CREATE(list); + + for(i = 0; i < 3; i++) + { + ASSERT_RC(getdns_list_set_int(list, i, i), GETDNS_RETURN_GOOD, + "Return code from getdns_list_set_int()"); + } + + ASSERT_RC(getdns_list_get_length(list, &length), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_length()"); + + ck_assert_msg(length == 3, "Expected length == 3, got %d", length); + + LIST_DESTROY(list); + } + END_TEST + + START_TEST (getdns_list_get_length_4) + { + /* + * Create a list (empty) and get the length + * expect: GETDNS_RETURN_GOOD + * length = 3 + */ + struct getdns_list *list = NULL; + size_t length; + + LIST_CREATE(list); + + ASSERT_RC(getdns_list_get_length(list, &length), + GETDNS_RETURN_GOOD, "Return code from getdns_list_get_length()"); + + ck_assert_msg(length == 0, "Expected length == 3, got %d", length); + + LIST_DESTROY(list); + } + END_TEST + + Suite * + getdns_list_get_length_suite (void) + { + Suite *s = suite_create ("getdns_list_get_length()"); + + /* Negative test caseis */ + TCase *tc_neg = tcase_create("Negative"); + tcase_add_test(tc_neg, getdns_list_get_length_1); + tcase_add_test(tc_neg, getdns_list_get_length_2); + suite_add_tcase(s, tc_neg); + + /* Positive test cases */ + TCase *tc_pos = tcase_create("Positive"); + tcase_add_test(tc_pos, getdns_list_get_length_3); + tcase_add_test(tc_pos, getdns_list_get_length_4); + suite_add_tcase(s, tc_pos); + + return s; + } + +#endif