diff --git a/lib/dns/tests/rdata_test.c b/lib/dns/tests/rdata_test.c index dc95ba6e26..1f93cf213f 100644 --- a/lib/dns/tests/rdata_test.c +++ b/lib/dns/tests/rdata_test.c @@ -152,6 +152,88 @@ wire_to_rdata(const unsigned char *src, size_t srclen, return (result); } +/* + * Call dns_rdata_towire() for rdata and write to result to dst. + */ +static isc_result_t +rdata_towire(dns_rdata_t *rdata, unsigned char *dst, size_t dstlen, + size_t *length) +{ + isc_buffer_t target; + dns_compress_t cctx; + isc_result_t result; + + /* + * Initialize target buffer. + */ + isc_buffer_init(&target, dst, dstlen); + + /* + * Try converting input data into uncompressed wire form. + */ + dns_compress_init(&cctx, -1, dt_mctx); + result = dns_rdata_towire(rdata, &cctx, &target); + dns_compress_invalidate(&cctx); + + *length = isc_buffer_usedlength(&target); + + return (result); +} + +static isc_result_t +additionaldata_cb(void *arg, const dns_name_t *name, dns_rdatatype_t qtype) { + UNUSED(arg); + UNUSED(name); + UNUSED(qtype); + return (ISC_R_SUCCESS); +} + +/* + * call dns_rdata_additionaldata() for rdata. + */ +static isc_result_t +rdata_additionadata(dns_rdata_t *rdata) { + return (dns_rdata_additionaldata(rdata, additionaldata_cb, NULL)); +} + +/* + * Call dns_rdata_checknames() with various owner names chosen to + * match well known forms. + * + * We are currently only checking that the calls do not trigger + * assertion failures. + * + * XXXMPA A future extention could be to record the expected + * result and the expected value of 'bad'. + */ +static void +rdata_checknames(dns_rdata_t *rdata) { + dns_fixedname_t fixed, bfixed; + dns_name_t *name, *bad; + isc_result_t result; + + name = dns_fixedname_initname(&fixed); + bad = dns_fixedname_initname(&bfixed); + + (void) dns_rdata_checknames(rdata, dns_rootname, NULL); + (void) dns_rdata_checknames(rdata, dns_rootname, bad); + + result = dns_name_fromstring(name, "example.net", 0, NULL); + assert_int_equal(result, ISC_R_SUCCESS); + (void) dns_rdata_checknames(rdata, name, NULL); + (void) dns_rdata_checknames(rdata, name, bad); + + result = dns_name_fromstring(name, "in-addr.arpa", 0, NULL); + assert_int_equal(result, ISC_R_SUCCESS); + (void) dns_rdata_checknames(rdata, name, NULL); + (void) dns_rdata_checknames(rdata, name, bad); + + result = dns_name_fromstring(name, "ip6.arpa", 0, NULL); + assert_int_equal(result, ISC_R_SUCCESS); + (void) dns_rdata_checknames(rdata, name, NULL); + (void) dns_rdata_checknames(rdata, name, bad); +} + /* * Test whether converting rdata to a type-specific struct and then back to * rdata results in the same uncompressed wire form. This checks whether @@ -206,11 +288,12 @@ static void check_text_ok_single(const text_ok_t *text_ok, dns_rdataclass_t rdclass, dns_rdatatype_t type, size_t structsize) { - unsigned char buf_fromtext[1024], buf_fromwire[1024]; + unsigned char buf_fromtext[1024], buf_fromwire[1024], buf_towire[1024]; dns_rdata_t rdata = DNS_RDATA_INIT, rdata2 = DNS_RDATA_INIT; char buf_totext[1024] = { 0 }; isc_buffer_t target; isc_result_t result; + size_t length = 0; /* * Try converting text form RDATA into uncompressed wire form. @@ -269,6 +352,25 @@ check_text_ok_single(const text_ok_t *text_ok, dns_rdataclass_t rdclass, assert_int_equal(rdata.length, rdata2.length); assert_memory_equal(rdata.data, buf_fromwire, rdata.length); + /* + * Ensure that fromtext_*() output is valid input for towire_*(). + */ + result = rdata_towire(&rdata, buf_towire, sizeof(buf_towire), &length); + assert_int_equal(result, ISC_R_SUCCESS); + assert_int_equal(rdata.length, length); + assert_memory_equal(rdata.data, buf_towire, length); + + /* + * Test that additionaldata_*() succeeded. + */ + result = rdata_additionadata(&rdata); + assert_int_equal(result, ISC_R_SUCCESS); + + /* + * Exercise checknames_*(). + */ + rdata_checknames(&rdata); + /* * Perform two-way conversion checks between uncompressed wire form and * type-specific struct. @@ -380,9 +482,10 @@ static void check_wire_ok_single(const wire_ok_t *wire_ok, dns_rdataclass_t rdclass, dns_rdatatype_t type, size_t structsize) { - unsigned char buf[1024]; + unsigned char buf[1024], buf_towire[1024]; isc_result_t result; dns_rdata_t rdata = DNS_RDATA_INIT; + size_t length = 0; /* * Try converting wire data into uncompressed wire form. @@ -397,6 +500,11 @@ check_wire_ok_single(const wire_ok_t *wire_ok, dns_rdataclass_t rdclass, } else { assert_int_not_equal(result, ISC_R_SUCCESS); } + + if (result != ISC_R_SUCCESS) { + return; + } + /* * If data was parsed correctly, perform two-way conversion checks * between uncompressed wire form and type-specific struct. @@ -407,13 +515,30 @@ check_wire_ok_single(const wire_ok_t *wire_ok, dns_rdataclass_t rdclass, * - uncompressed wire form and text form, * - uncompressed wire form and multi-line text form. */ - if (result == ISC_R_SUCCESS) { - check_struct_conversions(&rdata, structsize); - if (!dns_rdatatype_ismeta(rdata.type)) { - check_text_conversions(&rdata); - check_multiline_text_conversions(&rdata); - } + check_struct_conversions(&rdata, structsize); + if (!dns_rdatatype_ismeta(rdata.type)) { + check_text_conversions(&rdata); + check_multiline_text_conversions(&rdata); } + + /* + * Ensure that fromwire_*() output is valid input for towire_*(). + */ + result = rdata_towire(&rdata, buf_towire, sizeof(buf_towire), &length); + assert_int_equal(result, ISC_R_SUCCESS); + assert_int_equal(rdata.length, length); + assert_memory_equal(rdata.data, buf_towire, length); + + /* + * Test that additionaldata_*() succeeded. + */ + result = rdata_additionadata(&rdata); + assert_int_equal(result, ISC_R_SUCCESS); + + /* + * Exercise checknames_*(). + */ + rdata_checknames(&rdata); } /*