1238104Sdes/* 2238104Sdes * host2str.c 3238104Sdes * 4238104Sdes * conversion routines from the host format 5238104Sdes * to the presentation format (strings) 6238104Sdes * 7238104Sdes * a Net::DNS like library for C 8238104Sdes * 9238104Sdes * (c) NLnet Labs, 2004-2006 10238104Sdes * 11238104Sdes * See the file LICENSE for the license 12238104Sdes */ 13238104Sdes#include <ldns/config.h> 14238104Sdes 15238104Sdes#include <ldns/ldns.h> 16238104Sdes 17238104Sdes#include <limits.h> 18238104Sdes 19238104Sdes#ifdef HAVE_SYS_SOCKET_H 20238104Sdes#include <sys/socket.h> 21238104Sdes#endif 22238104Sdes#ifdef HAVE_ARPA_INET_H 23238104Sdes#include <arpa/inet.h> 24238104Sdes#endif 25238104Sdes#ifdef HAVE_NETDB_H 26238104Sdes#include <netdb.h> 27238104Sdes#endif 28238104Sdes#include <time.h> 29238104Sdes#include <sys/time.h> 30238104Sdes 31238104Sdes#ifndef INET_ADDRSTRLEN 32238104Sdes#define INET_ADDRSTRLEN 16 33238104Sdes#endif 34238104Sdes#ifndef INET6_ADDRSTRLEN 35238104Sdes#define INET6_ADDRSTRLEN 46 36238104Sdes#endif 37238104Sdes 38238104Sdes/* lookup tables for standard DNS stuff */ 39238104Sdes 40238104Sdes/* Taken from RFC 2535, section 7. */ 41238104Sdesldns_lookup_table ldns_algorithms[] = { 42238104Sdes { LDNS_RSAMD5, "RSAMD5" }, 43238104Sdes { LDNS_DH, "DH" }, 44238104Sdes { LDNS_DSA, "DSA" }, 45238104Sdes { LDNS_ECC, "ECC" }, 46238104Sdes { LDNS_RSASHA1, "RSASHA1" }, 47238104Sdes { LDNS_DSA_NSEC3, "DSA-NSEC3-SHA1" }, 48238104Sdes { LDNS_RSASHA1_NSEC3, "RSASHA1-NSEC3-SHA1" }, 49238104Sdes#ifdef USE_SHA2 50238104Sdes { LDNS_RSASHA256, "RSASHA256"}, 51238104Sdes { LDNS_RSASHA512, "RSASHA512"}, 52238104Sdes#endif 53238104Sdes#ifdef USE_GOST 54238104Sdes { LDNS_ECC_GOST, "ECC-GOST"}, 55238104Sdes#endif 56238104Sdes#ifdef USE_ECDSA 57238104Sdes { LDNS_ECDSAP256SHA256, "ECDSAP256SHA256"}, 58238104Sdes { LDNS_ECDSAP384SHA384, "ECDSAP384SHA384"}, 59238104Sdes#endif 60238104Sdes { LDNS_INDIRECT, "INDIRECT" }, 61238104Sdes { LDNS_PRIVATEDNS, "PRIVATEDNS" }, 62238104Sdes { LDNS_PRIVATEOID, "PRIVATEOID" }, 63238104Sdes { 0, NULL } 64238104Sdes}; 65238104Sdes 66238104Sdes/* Taken from RFC 4398 */ 67238104Sdesldns_lookup_table ldns_cert_algorithms[] = { 68238104Sdes { LDNS_CERT_PKIX, "PKIX" }, 69238104Sdes { LDNS_CERT_SPKI, "SPKI" }, 70238104Sdes { LDNS_CERT_PGP, "PGP" }, 71238104Sdes { LDNS_CERT_IPKIX, "IPKIX" }, 72238104Sdes { LDNS_CERT_ISPKI, "ISPKI" }, 73238104Sdes { LDNS_CERT_IPGP, "IPGP" }, 74238104Sdes { LDNS_CERT_ACPKIX, "ACPKIX" }, 75238104Sdes { LDNS_CERT_IACPKIX, "IACPKIX" }, 76238104Sdes { LDNS_CERT_URI, "URI" }, 77238104Sdes { LDNS_CERT_OID, "OID" }, 78238104Sdes { 0, NULL } 79238104Sdes}; 80238104Sdes 81238104Sdes/* classes */ 82238104Sdesldns_lookup_table ldns_rr_classes[] = { 83238104Sdes { LDNS_RR_CLASS_IN, "IN" }, 84238104Sdes { LDNS_RR_CLASS_CH, "CH" }, 85238104Sdes { LDNS_RR_CLASS_HS, "HS" }, 86238104Sdes { LDNS_RR_CLASS_NONE, "NONE" }, 87238104Sdes { LDNS_RR_CLASS_ANY, "ANY" }, 88238104Sdes { 0, NULL } 89238104Sdes}; 90238104Sdes 91238104Sdes/* if these are used elsewhere */ 92238104Sdesldns_lookup_table ldns_rcodes[] = { 93238104Sdes { LDNS_RCODE_NOERROR, "NOERROR" }, 94238104Sdes { LDNS_RCODE_FORMERR, "FORMERR" }, 95238104Sdes { LDNS_RCODE_SERVFAIL, "SERVFAIL" }, 96238104Sdes { LDNS_RCODE_NXDOMAIN, "NXDOMAIN" }, 97238104Sdes { LDNS_RCODE_NOTIMPL, "NOTIMPL" }, 98238104Sdes { LDNS_RCODE_REFUSED, "REFUSED" }, 99238104Sdes { LDNS_RCODE_YXDOMAIN, "YXDOMAIN" }, 100238104Sdes { LDNS_RCODE_YXRRSET, "YXRRSET" }, 101238104Sdes { LDNS_RCODE_NXRRSET, "NXRRSET" }, 102238104Sdes { LDNS_RCODE_NOTAUTH, "NOTAUTH" }, 103238104Sdes { LDNS_RCODE_NOTZONE, "NOTZONE" }, 104238104Sdes { 0, NULL } 105238104Sdes}; 106238104Sdes 107238104Sdesldns_lookup_table ldns_opcodes[] = { 108238104Sdes { LDNS_PACKET_QUERY, "QUERY" }, 109238104Sdes { LDNS_PACKET_IQUERY, "IQUERY" }, 110238104Sdes { LDNS_PACKET_STATUS, "STATUS" }, 111238104Sdes { LDNS_PACKET_NOTIFY, "NOTIFY" }, 112238104Sdes { LDNS_PACKET_UPDATE, "UPDATE" }, 113238104Sdes { 0, NULL } 114238104Sdes}; 115238104Sdes 116238104Sdesconst ldns_output_format ldns_output_format_nocomments_record = { 0, NULL }; 117238104Sdesconst ldns_output_format *ldns_output_format_nocomments 118238104Sdes = &ldns_output_format_nocomments_record; 119238104Sdesconst ldns_output_format ldns_output_format_onlykeyids_record = { 120238104Sdes LDNS_COMMENT_KEY, NULL 121238104Sdes}; 122238104Sdesconst ldns_output_format *ldns_output_format_onlykeyids 123238104Sdes = &ldns_output_format_onlykeyids_record; 124238104Sdesconst ldns_output_format *ldns_output_format_default 125238104Sdes = &ldns_output_format_onlykeyids_record; 126246854Sdes 127238104Sdesconst ldns_output_format ldns_output_format_bubblebabble_record = { 128238104Sdes LDNS_COMMENT_KEY | LDNS_COMMENT_BUBBLEBABBLE | LDNS_COMMENT_FLAGS, NULL 129238104Sdes}; 130238104Sdesconst ldns_output_format *ldns_output_format_bubblebabble 131238104Sdes = &ldns_output_format_bubblebabble_record; 132238104Sdes 133266114Sdesstatic bool 134266114Sdesldns_output_format_covers_type(const ldns_output_format* fmt, ldns_rr_type t) 135266114Sdes{ 136266114Sdes return fmt && (fmt->flags & LDNS_FMT_RFC3597) && 137266114Sdes ((ldns_output_format_storage*)fmt)->bitmap && 138266114Sdes ldns_nsec_bitmap_covers_type( 139266114Sdes ((ldns_output_format_storage*)fmt)->bitmap, t); 140266114Sdes} 141266114Sdes 142238104Sdesldns_status 143266114Sdesldns_output_format_set_type(ldns_output_format* fmt, ldns_rr_type t) 144266114Sdes{ 145266114Sdes ldns_output_format_storage* fmt_st = (ldns_output_format_storage*)fmt; 146266114Sdes ldns_status s; 147266114Sdes 148266114Sdes assert(fmt != NULL); 149266114Sdes 150266114Sdes if (!(fmt_st->flags & LDNS_FMT_RFC3597)) { 151266114Sdes ldns_output_format_set(fmt, LDNS_FMT_RFC3597); 152266114Sdes } 153266114Sdes if (! fmt_st->bitmap) { 154266114Sdes s = ldns_rdf_bitmap_known_rr_types_space(&fmt_st->bitmap); 155266114Sdes if (s != LDNS_STATUS_OK) { 156266114Sdes return s; 157266114Sdes } 158266114Sdes } 159266114Sdes return ldns_nsec_bitmap_set_type(fmt_st->bitmap, t); 160266114Sdes} 161266114Sdes 162266114Sdesldns_status 163266114Sdesldns_output_format_clear_type(ldns_output_format* fmt, ldns_rr_type t) 164266114Sdes{ 165266114Sdes ldns_output_format_storage* fmt_st = (ldns_output_format_storage*)fmt; 166266114Sdes ldns_status s; 167266114Sdes 168266114Sdes assert(fmt != NULL); 169266114Sdes 170266114Sdes if (!(fmt_st->flags & LDNS_FMT_RFC3597)) { 171266114Sdes ldns_output_format_set(fmt, LDNS_FMT_RFC3597); 172266114Sdes } 173266114Sdes if (! fmt_st->bitmap) { 174266114Sdes s = ldns_rdf_bitmap_known_rr_types(&fmt_st->bitmap); 175266114Sdes if (s != LDNS_STATUS_OK) { 176266114Sdes return s; 177266114Sdes } 178266114Sdes } 179266114Sdes return ldns_nsec_bitmap_clear_type(fmt_st->bitmap, t); 180266114Sdes} 181266114Sdes 182266114Sdesldns_status 183238104Sdesldns_pkt_opcode2buffer_str(ldns_buffer *output, ldns_pkt_opcode opcode) 184238104Sdes{ 185238104Sdes ldns_lookup_table *lt = ldns_lookup_by_id(ldns_opcodes, opcode); 186238104Sdes if (lt && lt->name) { 187238104Sdes ldns_buffer_printf(output, "%s", lt->name); 188238104Sdes } else { 189238104Sdes ldns_buffer_printf(output, "OPCODE%u", opcode); 190238104Sdes } 191238104Sdes return ldns_buffer_status(output); 192238104Sdes} 193238104Sdes 194238104Sdesldns_status 195238104Sdesldns_pkt_rcode2buffer_str(ldns_buffer *output, ldns_pkt_rcode rcode) 196238104Sdes{ 197238104Sdes ldns_lookup_table *lt = ldns_lookup_by_id(ldns_rcodes, rcode); 198238104Sdes if (lt && lt->name) { 199238104Sdes ldns_buffer_printf(output, "%s", lt->name); 200238104Sdes } else { 201238104Sdes ldns_buffer_printf(output, "RCODE%u", rcode); 202238104Sdes } 203238104Sdes return ldns_buffer_status(output); 204238104Sdes} 205238104Sdes 206238104Sdesldns_status 207238104Sdesldns_algorithm2buffer_str(ldns_buffer *output, 208238104Sdes ldns_algorithm algorithm) 209238104Sdes{ 210238104Sdes ldns_lookup_table *lt = ldns_lookup_by_id(ldns_algorithms, 211238104Sdes algorithm); 212238104Sdes if (lt && lt->name) { 213238104Sdes ldns_buffer_printf(output, "%s", lt->name); 214238104Sdes } else { 215238104Sdes ldns_buffer_printf(output, "ALG%u", algorithm); 216238104Sdes } 217238104Sdes return ldns_buffer_status(output); 218238104Sdes} 219238104Sdes 220238104Sdesldns_status 221238104Sdesldns_cert_algorithm2buffer_str(ldns_buffer *output, 222238104Sdes ldns_cert_algorithm cert_algorithm) 223238104Sdes{ 224238104Sdes ldns_lookup_table *lt = ldns_lookup_by_id(ldns_cert_algorithms, 225238104Sdes cert_algorithm); 226238104Sdes if (lt && lt->name) { 227238104Sdes ldns_buffer_printf(output, "%s", lt->name); 228238104Sdes } else { 229238104Sdes ldns_buffer_printf(output, "CERT_ALG%u", 230238104Sdes cert_algorithm); 231238104Sdes } 232238104Sdes return ldns_buffer_status(output); 233238104Sdes} 234238104Sdes 235238104Sdeschar * 236238104Sdesldns_pkt_opcode2str(ldns_pkt_opcode opcode) 237238104Sdes{ 238238104Sdes char *str; 239238104Sdes ldns_buffer *buf; 240238104Sdes 241238104Sdes buf = ldns_buffer_new(12); 242238104Sdes if (!buf) { 243238104Sdes return NULL; 244238104Sdes } 245238104Sdes 246238104Sdes str = NULL; 247238104Sdes if (ldns_pkt_opcode2buffer_str(buf, opcode) == LDNS_STATUS_OK) { 248246854Sdes str = ldns_buffer_export2str(buf); 249238104Sdes } 250238104Sdes 251238104Sdes ldns_buffer_free(buf); 252238104Sdes return str; 253238104Sdes} 254238104Sdes 255238104Sdeschar * 256238104Sdesldns_pkt_rcode2str(ldns_pkt_rcode rcode) 257238104Sdes{ 258238104Sdes char *str; 259238104Sdes ldns_buffer *buf; 260238104Sdes 261238104Sdes buf = ldns_buffer_new(10); 262238104Sdes if (!buf) { 263238104Sdes return NULL; 264238104Sdes } 265238104Sdes 266238104Sdes str = NULL; 267238104Sdes if (ldns_pkt_rcode2buffer_str(buf, rcode) == LDNS_STATUS_OK) { 268246854Sdes str = ldns_buffer_export2str(buf); 269238104Sdes } 270238104Sdes 271238104Sdes ldns_buffer_free(buf); 272238104Sdes return str; 273238104Sdes} 274238104Sdes 275238104Sdeschar * 276238104Sdesldns_pkt_algorithm2str(ldns_algorithm algorithm) 277238104Sdes{ 278238104Sdes char *str; 279238104Sdes ldns_buffer *buf; 280238104Sdes 281238104Sdes buf = ldns_buffer_new(10); 282238104Sdes if (!buf) { 283238104Sdes return NULL; 284238104Sdes } 285238104Sdes 286238104Sdes str = NULL; 287238104Sdes if (ldns_algorithm2buffer_str(buf, algorithm) 288238104Sdes == LDNS_STATUS_OK) { 289246854Sdes str = ldns_buffer_export2str(buf); 290238104Sdes } 291238104Sdes 292238104Sdes ldns_buffer_free(buf); 293238104Sdes return str; 294238104Sdes} 295238104Sdes 296238104Sdeschar * 297238104Sdesldns_pkt_cert_algorithm2str(ldns_cert_algorithm cert_algorithm) 298238104Sdes{ 299238104Sdes char *str; 300238104Sdes ldns_buffer *buf; 301238104Sdes 302238104Sdes buf = ldns_buffer_new(10); 303238104Sdes if (!buf) { 304238104Sdes return NULL; 305238104Sdes } 306238104Sdes 307238104Sdes str = NULL; 308238104Sdes if (ldns_cert_algorithm2buffer_str(buf, cert_algorithm) 309238104Sdes == LDNS_STATUS_OK) { 310246854Sdes str = ldns_buffer_export2str(buf); 311238104Sdes } 312238104Sdes 313238104Sdes ldns_buffer_free(buf); 314238104Sdes return str; 315238104Sdes} 316238104Sdes 317238104Sdes 318238104Sdes/* do NOT pass compressed data here :p */ 319238104Sdesldns_status 320238104Sdesldns_rdf2buffer_str_dname(ldns_buffer *output, const ldns_rdf *dname) 321238104Sdes{ 322238104Sdes /* can we do with 1 pos var? or without at all? */ 323238104Sdes uint8_t src_pos = 0; 324238104Sdes uint8_t len; 325238104Sdes uint8_t *data; 326238104Sdes uint8_t i; 327238104Sdes unsigned char c; 328238104Sdes 329238104Sdes data = (uint8_t*)ldns_rdf_data(dname); 330238104Sdes len = data[src_pos]; 331238104Sdes 332238104Sdes if (ldns_rdf_size(dname) > LDNS_MAX_DOMAINLEN) { 333238104Sdes /* too large, return */ 334238104Sdes return LDNS_STATUS_DOMAINNAME_OVERFLOW; 335238104Sdes } 336238104Sdes 337238104Sdes /* special case: root label */ 338238104Sdes if (1 == ldns_rdf_size(dname)) { 339238104Sdes ldns_buffer_printf(output, "."); 340238104Sdes } else { 341238104Sdes while ((len > 0) && src_pos < ldns_rdf_size(dname)) { 342238104Sdes src_pos++; 343238104Sdes for(i = 0; i < len; i++) { 344238104Sdes /* paranoia check for various 'strange' 345238104Sdes characters in dnames 346238104Sdes */ 347238104Sdes c = (unsigned char) data[src_pos]; 348238104Sdes if(c == '.' || c == ';' || 349238104Sdes c == '(' || c == ')' || 350238104Sdes c == '\\') { 351238104Sdes ldns_buffer_printf(output, "\\%c", 352238104Sdes data[src_pos]); 353238104Sdes } else if (!(isascii(c) && isgraph(c))) { 354238104Sdes ldns_buffer_printf(output, "\\%03u", 355238104Sdes data[src_pos]); 356238104Sdes } else { 357238104Sdes ldns_buffer_printf(output, "%c", data[src_pos]); 358238104Sdes } 359238104Sdes src_pos++; 360238104Sdes } 361238104Sdes 362238104Sdes if (src_pos < ldns_rdf_size(dname)) { 363238104Sdes ldns_buffer_printf(output, "."); 364238104Sdes } 365238104Sdes len = data[src_pos]; 366238104Sdes } 367238104Sdes } 368238104Sdes return ldns_buffer_status(output); 369238104Sdes} 370238104Sdes 371238104Sdesldns_status 372238104Sdesldns_rdf2buffer_str_int8(ldns_buffer *output, const ldns_rdf *rdf) 373238104Sdes{ 374238104Sdes uint8_t data = ldns_rdf_data(rdf)[0]; 375238104Sdes ldns_buffer_printf(output, "%lu", (unsigned long) data); 376238104Sdes return ldns_buffer_status(output); 377238104Sdes} 378238104Sdes 379238104Sdesldns_status 380238104Sdesldns_rdf2buffer_str_int16(ldns_buffer *output, const ldns_rdf *rdf) 381238104Sdes{ 382238104Sdes uint16_t data = ldns_read_uint16(ldns_rdf_data(rdf)); 383238104Sdes ldns_buffer_printf(output, "%lu", (unsigned long) data); 384238104Sdes return ldns_buffer_status(output); 385238104Sdes} 386238104Sdes 387238104Sdesldns_status 388238104Sdesldns_rdf2buffer_str_int32(ldns_buffer *output, const ldns_rdf *rdf) 389238104Sdes{ 390238104Sdes uint32_t data = ldns_read_uint32(ldns_rdf_data(rdf)); 391238104Sdes ldns_buffer_printf(output, "%lu", (unsigned long) data); 392238104Sdes return ldns_buffer_status(output); 393238104Sdes} 394238104Sdes 395238104Sdesldns_status 396238104Sdesldns_rdf2buffer_str_time(ldns_buffer *output, const ldns_rdf *rdf) 397238104Sdes{ 398238104Sdes /* create a YYYYMMDDHHMMSS string if possible */ 399238104Sdes struct tm tm; 400238104Sdes char date_buf[16]; 401238104Sdes 402238104Sdes memset(&tm, 0, sizeof(tm)); 403238104Sdes if (ldns_serial_arithmitics_gmtime_r(ldns_rdf2native_int32(rdf), time(NULL), &tm) 404238104Sdes && strftime(date_buf, 15, "%Y%m%d%H%M%S", &tm)) { 405238104Sdes ldns_buffer_printf(output, "%s", date_buf); 406238104Sdes } 407238104Sdes return ldns_buffer_status(output); 408238104Sdes} 409238104Sdes 410238104Sdesldns_status 411238104Sdesldns_rdf2buffer_str_a(ldns_buffer *output, const ldns_rdf *rdf) 412238104Sdes{ 413238104Sdes char str[INET_ADDRSTRLEN]; 414238104Sdes 415238104Sdes if (inet_ntop(AF_INET, ldns_rdf_data(rdf), str, INET_ADDRSTRLEN)) { 416238104Sdes ldns_buffer_printf(output, "%s", str); 417238104Sdes } 418238104Sdes return ldns_buffer_status(output); 419238104Sdes} 420238104Sdes 421238104Sdesldns_status 422238104Sdesldns_rdf2buffer_str_aaaa(ldns_buffer *output, const ldns_rdf *rdf) 423238104Sdes{ 424238104Sdes char str[INET6_ADDRSTRLEN]; 425238104Sdes 426238104Sdes if (inet_ntop(AF_INET6, ldns_rdf_data(rdf), str, INET6_ADDRSTRLEN)) { 427238104Sdes ldns_buffer_printf(output, "%s", str); 428238104Sdes } 429238104Sdes 430238104Sdes return ldns_buffer_status(output); 431238104Sdes} 432238104Sdes 433266114Sdesstatic void 434266114Sdesldns_characters2buffer_str(ldns_buffer* output, 435266114Sdes size_t amount, const uint8_t* characters) 436238104Sdes{ 437266114Sdes uint8_t ch; 438266114Sdes while (amount > 0) { 439266114Sdes ch = *characters++; 440266114Sdes if (isprint((int)ch) || ch == '\t') { 441266114Sdes if (ch == '\"' || ch == '\\') 442238104Sdes ldns_buffer_printf(output, "\\%c", ch); 443238104Sdes else 444238104Sdes ldns_buffer_printf(output, "%c", ch); 445238104Sdes } else { 446238104Sdes ldns_buffer_printf(output, "\\%03u", 447238104Sdes (unsigned)(uint8_t) ch); 448238104Sdes } 449266114Sdes amount--; 450238104Sdes } 451266114Sdes} 452266114Sdes 453266114Sdesldns_status 454266114Sdesldns_rdf2buffer_str_str(ldns_buffer *output, const ldns_rdf *rdf) 455266114Sdes{ 456266114Sdes if(ldns_rdf_size(rdf) < 1) { 457266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 458266114Sdes } 459266114Sdes if((int)ldns_rdf_size(rdf) < (int)ldns_rdf_data(rdf)[0] + 1) { 460266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 461266114Sdes } 462238104Sdes ldns_buffer_printf(output, "\""); 463266114Sdes ldns_characters2buffer_str(output, 464266114Sdes ldns_rdf_data(rdf)[0], ldns_rdf_data(rdf) + 1); 465266114Sdes ldns_buffer_printf(output, "\""); 466238104Sdes return ldns_buffer_status(output); 467238104Sdes} 468238104Sdes 469238104Sdesldns_status 470238104Sdesldns_rdf2buffer_str_b64(ldns_buffer *output, const ldns_rdf *rdf) 471238104Sdes{ 472238104Sdes size_t size = ldns_b64_ntop_calculate_size(ldns_rdf_size(rdf)); 473238104Sdes char *b64 = LDNS_XMALLOC(char, size); 474238104Sdes if(!b64) return LDNS_STATUS_MEM_ERR; 475238104Sdes if (ldns_b64_ntop(ldns_rdf_data(rdf), ldns_rdf_size(rdf), b64, size)) { 476238104Sdes ldns_buffer_printf(output, "%s", b64); 477238104Sdes } 478238104Sdes LDNS_FREE(b64); 479238104Sdes return ldns_buffer_status(output); 480238104Sdes} 481238104Sdes 482238104Sdesldns_status 483238104Sdesldns_rdf2buffer_str_b32_ext(ldns_buffer *output, const ldns_rdf *rdf) 484238104Sdes{ 485238104Sdes size_t size; 486238104Sdes char *b32; 487238104Sdes if(ldns_rdf_size(rdf) == 0) 488238104Sdes return LDNS_STATUS_OK; 489238104Sdes /* remove -1 for the b32-hash-len octet */ 490238104Sdes size = ldns_b32_ntop_calculate_size(ldns_rdf_size(rdf) - 1); 491238104Sdes /* add one for the end nul for the string */ 492238104Sdes b32 = LDNS_XMALLOC(char, size + 1); 493238104Sdes if(!b32) return LDNS_STATUS_MEM_ERR; 494238104Sdes size = (size_t) ldns_b32_ntop_extended_hex(ldns_rdf_data(rdf) + 1, 495238104Sdes ldns_rdf_size(rdf) - 1, b32, size+1); 496238104Sdes if (size > 0) { 497238104Sdes ldns_buffer_printf(output, "%s", b32); 498238104Sdes } 499238104Sdes LDNS_FREE(b32); 500238104Sdes return ldns_buffer_status(output); 501238104Sdes} 502238104Sdes 503238104Sdesldns_status 504238104Sdesldns_rdf2buffer_str_hex(ldns_buffer *output, const ldns_rdf *rdf) 505238104Sdes{ 506238104Sdes size_t i; 507238104Sdes for (i = 0; i < ldns_rdf_size(rdf); i++) { 508238104Sdes ldns_buffer_printf(output, "%02x", ldns_rdf_data(rdf)[i]); 509238104Sdes } 510238104Sdes 511238104Sdes return ldns_buffer_status(output); 512238104Sdes} 513238104Sdes 514266114Sdesstatic ldns_status 515266114Sdesldns_rdf2buffer_str_type_fmt(ldns_buffer *output, 516266114Sdes const ldns_output_format* fmt, const ldns_rdf *rdf) 517238104Sdes{ 518238104Sdes uint16_t data = ldns_read_uint16(ldns_rdf_data(rdf)); 519238104Sdes 520266114Sdes if (! ldns_output_format_covers_type(fmt, data) && 521266114Sdes ldns_rr_descript(data) && 522266114Sdes ldns_rr_descript(data)->_name) { 523266114Sdes 524266114Sdes ldns_buffer_printf(output, "%s",ldns_rr_descript(data)->_name); 525238104Sdes } else { 526238104Sdes ldns_buffer_printf(output, "TYPE%u", data); 527238104Sdes } 528266114Sdes return ldns_buffer_status(output); 529238104Sdes} 530238104Sdes 531238104Sdesldns_status 532266114Sdesldns_rdf2buffer_str_type(ldns_buffer *output, const ldns_rdf *rdf) 533266114Sdes{ 534266114Sdes return ldns_rdf2buffer_str_type_fmt(output, 535266114Sdes ldns_output_format_default, rdf); 536266114Sdes} 537266114Sdes 538266114Sdesldns_status 539238104Sdesldns_rdf2buffer_str_class(ldns_buffer *output, const ldns_rdf *rdf) 540238104Sdes{ 541238104Sdes uint16_t data = ldns_read_uint16(ldns_rdf_data(rdf)); 542238104Sdes ldns_lookup_table *lt; 543238104Sdes 544238104Sdes lt = ldns_lookup_by_id(ldns_rr_classes, (int) data); 545238104Sdes if (lt) { 546238104Sdes ldns_buffer_printf(output, "\t%s", lt->name); 547238104Sdes } else { 548238104Sdes ldns_buffer_printf(output, "\tCLASS%d", data); 549238104Sdes } 550238104Sdes return ldns_buffer_status(output); 551238104Sdes} 552238104Sdes 553238104Sdesldns_status 554238104Sdesldns_rdf2buffer_str_cert_alg(ldns_buffer *output, const ldns_rdf *rdf) 555238104Sdes{ 556238104Sdes uint16_t data = ldns_read_uint16(ldns_rdf_data(rdf)); 557238104Sdes ldns_lookup_table *lt; 558238104Sdes lt = ldns_lookup_by_id(ldns_cert_algorithms, (int) data); 559238104Sdes if (lt) { 560238104Sdes ldns_buffer_printf(output, "%s", lt->name); 561238104Sdes } else { 562238104Sdes ldns_buffer_printf(output, "%d", data); 563238104Sdes } 564238104Sdes return ldns_buffer_status(output); 565238104Sdes} 566238104Sdes 567238104Sdesldns_status 568238104Sdesldns_rdf2buffer_str_alg(ldns_buffer *output, const ldns_rdf *rdf) 569238104Sdes{ 570238104Sdes /* don't use algorithm mnemonics in the presentation format 571238104Sdes this kind of got sneaked into the rfc's */ 572238104Sdes uint8_t data = ldns_rdf_data(rdf)[0]; 573238104Sdes ldns_buffer_printf(output, "%d", data); 574238104Sdes return ldns_buffer_status(output); 575238104Sdes} 576238104Sdes 577238104Sdesstatic void 578238104Sdesloc_cm_print(ldns_buffer *output, uint8_t mantissa, uint8_t exponent) 579238104Sdes{ 580238104Sdes uint8_t i; 581238104Sdes /* is it 0.<two digits> ? */ 582238104Sdes if(exponent < 2) { 583238104Sdes if(exponent == 1) 584238104Sdes mantissa *= 10; 585238104Sdes ldns_buffer_printf(output, "0.%02ld", (long)mantissa); 586238104Sdes return; 587238104Sdes } 588238104Sdes /* always <digit><string of zeros> */ 589238104Sdes ldns_buffer_printf(output, "%d", (int)mantissa); 590238104Sdes for(i=0; i<exponent-2; i++) 591238104Sdes ldns_buffer_printf(output, "0"); 592238104Sdes} 593238104Sdes 594238104Sdesldns_status 595238104Sdesldns_rr_type2buffer_str(ldns_buffer *output, const ldns_rr_type type) 596238104Sdes{ 597238104Sdes const ldns_rr_descriptor *descriptor; 598238104Sdes 599238104Sdes descriptor = ldns_rr_descript(type); 600238104Sdes 601238104Sdes if (descriptor && descriptor->_name) { 602238104Sdes ldns_buffer_printf(output, "%s", descriptor->_name); 603238104Sdes } else { 604238104Sdes /* exceptions for pseudotypes */ 605238104Sdes switch (type) { 606238104Sdes case LDNS_RR_TYPE_IXFR: 607238104Sdes ldns_buffer_printf(output, "IXFR"); 608238104Sdes break; 609238104Sdes case LDNS_RR_TYPE_AXFR: 610238104Sdes ldns_buffer_printf(output, "AXFR"); 611238104Sdes break; 612238104Sdes case LDNS_RR_TYPE_MAILA: 613238104Sdes ldns_buffer_printf(output, "MAILA"); 614238104Sdes break; 615238104Sdes case LDNS_RR_TYPE_MAILB: 616238104Sdes ldns_buffer_printf(output, "MAILB"); 617238104Sdes break; 618238104Sdes case LDNS_RR_TYPE_ANY: 619238104Sdes ldns_buffer_printf(output, "ANY"); 620238104Sdes break; 621238104Sdes default: 622238104Sdes ldns_buffer_printf(output, "TYPE%u", type); 623238104Sdes } 624238104Sdes } 625238104Sdes return ldns_buffer_status(output); 626238104Sdes} 627238104Sdes 628238104Sdeschar * 629238104Sdesldns_rr_type2str(const ldns_rr_type type) 630238104Sdes{ 631238104Sdes char *str; 632238104Sdes ldns_buffer *buf; 633238104Sdes 634238104Sdes buf = ldns_buffer_new(10); 635238104Sdes if (!buf) { 636238104Sdes return NULL; 637238104Sdes } 638238104Sdes 639238104Sdes str = NULL; 640238104Sdes if (ldns_rr_type2buffer_str(buf, type) == LDNS_STATUS_OK) { 641246854Sdes str = ldns_buffer_export2str(buf); 642238104Sdes } 643238104Sdes 644238104Sdes ldns_buffer_free(buf); 645238104Sdes return str; 646238104Sdes} 647238104Sdes 648238104Sdes 649238104Sdesldns_status 650238104Sdesldns_rr_class2buffer_str(ldns_buffer *output, 651238104Sdes const ldns_rr_class klass) 652238104Sdes{ 653238104Sdes ldns_lookup_table *lt; 654238104Sdes 655238104Sdes lt = ldns_lookup_by_id(ldns_rr_classes, klass); 656238104Sdes if (lt) { 657238104Sdes ldns_buffer_printf(output, "%s", lt->name); 658238104Sdes } else { 659238104Sdes ldns_buffer_printf(output, "CLASS%d", klass); 660238104Sdes } 661238104Sdes return ldns_buffer_status(output); 662238104Sdes} 663238104Sdes 664238104Sdeschar * 665238104Sdesldns_rr_class2str(const ldns_rr_class klass) 666238104Sdes{ 667238104Sdes ldns_buffer *buf; 668238104Sdes char *str; 669238104Sdes 670238104Sdes buf = ldns_buffer_new(10); 671238104Sdes if (!buf) { 672238104Sdes return NULL; 673238104Sdes } 674238104Sdes 675238104Sdes str = NULL; 676238104Sdes if (ldns_rr_class2buffer_str(buf, klass) == LDNS_STATUS_OK) { 677246854Sdes str = ldns_buffer_export2str(buf); 678238104Sdes } 679238104Sdes ldns_buffer_free(buf); 680238104Sdes return str; 681238104Sdes} 682238104Sdes 683238104Sdesldns_status 684238104Sdesldns_rdf2buffer_str_loc(ldns_buffer *output, const ldns_rdf *rdf) 685238104Sdes{ 686238104Sdes /* we could do checking (ie degrees < 90 etc)? */ 687266114Sdes uint8_t version; 688238104Sdes uint8_t size; 689238104Sdes uint8_t horizontal_precision; 690238104Sdes uint8_t vertical_precision; 691238104Sdes uint32_t longitude; 692238104Sdes uint32_t latitude; 693238104Sdes uint32_t altitude; 694238104Sdes char northerness; 695238104Sdes char easterness; 696238104Sdes uint32_t h; 697238104Sdes uint32_t m; 698238104Sdes double s; 699238104Sdes 700238104Sdes uint32_t equator = (uint32_t) ldns_power(2, 31); 701238104Sdes 702266114Sdes if(ldns_rdf_size(rdf) < 1) { 703266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 704266114Sdes } 705266114Sdes version = ldns_rdf_data(rdf)[0]; 706238104Sdes if (version == 0) { 707266114Sdes if(ldns_rdf_size(rdf) < 16) { 708266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 709266114Sdes } 710238104Sdes size = ldns_rdf_data(rdf)[1]; 711238104Sdes horizontal_precision = ldns_rdf_data(rdf)[2]; 712238104Sdes vertical_precision = ldns_rdf_data(rdf)[3]; 713238104Sdes 714238104Sdes latitude = ldns_read_uint32(&ldns_rdf_data(rdf)[4]); 715238104Sdes longitude = ldns_read_uint32(&ldns_rdf_data(rdf)[8]); 716238104Sdes altitude = ldns_read_uint32(&ldns_rdf_data(rdf)[12]); 717238104Sdes 718238104Sdes if (latitude > equator) { 719238104Sdes northerness = 'N'; 720238104Sdes latitude = latitude - equator; 721238104Sdes } else { 722238104Sdes northerness = 'S'; 723238104Sdes latitude = equator - latitude; 724238104Sdes } 725238104Sdes h = latitude / (1000 * 60 * 60); 726238104Sdes latitude = latitude % (1000 * 60 * 60); 727238104Sdes m = latitude / (1000 * 60); 728238104Sdes latitude = latitude % (1000 * 60); 729238104Sdes s = (double) latitude / 1000.0; 730238104Sdes ldns_buffer_printf(output, "%02u %02u %0.3f %c ", 731238104Sdes h, m, s, northerness); 732238104Sdes 733238104Sdes if (longitude > equator) { 734238104Sdes easterness = 'E'; 735238104Sdes longitude = longitude - equator; 736238104Sdes } else { 737238104Sdes easterness = 'W'; 738238104Sdes longitude = equator - longitude; 739238104Sdes } 740238104Sdes h = longitude / (1000 * 60 * 60); 741238104Sdes longitude = longitude % (1000 * 60 * 60); 742238104Sdes m = longitude / (1000 * 60); 743238104Sdes longitude = longitude % (1000 * 60); 744238104Sdes s = (double) longitude / (1000.0); 745238104Sdes ldns_buffer_printf(output, "%02u %02u %0.3f %c ", 746238104Sdes h, m, s, easterness); 747238104Sdes 748238104Sdes 749266114Sdes s = ((double) altitude) / 100; 750266114Sdes s -= 100000; 751238104Sdes 752238104Sdes if(altitude%100 != 0) 753238104Sdes ldns_buffer_printf(output, "%.2f", s); 754266114Sdes else 755238104Sdes ldns_buffer_printf(output, "%.0f", s); 756238104Sdes 757238104Sdes ldns_buffer_printf(output, "m "); 758238104Sdes 759238104Sdes loc_cm_print(output, (size & 0xf0) >> 4, size & 0x0f); 760238104Sdes ldns_buffer_printf(output, "m "); 761238104Sdes 762238104Sdes loc_cm_print(output, (horizontal_precision & 0xf0) >> 4, 763238104Sdes horizontal_precision & 0x0f); 764238104Sdes ldns_buffer_printf(output, "m "); 765238104Sdes 766238104Sdes loc_cm_print(output, (vertical_precision & 0xf0) >> 4, 767238104Sdes vertical_precision & 0x0f); 768238104Sdes ldns_buffer_printf(output, "m"); 769238104Sdes 770238104Sdes return ldns_buffer_status(output); 771238104Sdes } else { 772238104Sdes return ldns_rdf2buffer_str_hex(output, rdf); 773238104Sdes } 774238104Sdes} 775238104Sdes 776238104Sdesldns_status 777238104Sdesldns_rdf2buffer_str_unknown(ldns_buffer *output, const ldns_rdf *rdf) 778238104Sdes{ 779238104Sdes ldns_buffer_printf(output, "\\# %u ", ldns_rdf_size(rdf)); 780238104Sdes return ldns_rdf2buffer_str_hex(output, rdf); 781238104Sdes} 782238104Sdes 783238104Sdesldns_status 784238104Sdesldns_rdf2buffer_str_nsap(ldns_buffer *output, const ldns_rdf *rdf) 785238104Sdes{ 786238104Sdes ldns_buffer_printf(output, "0x"); 787238104Sdes return ldns_rdf2buffer_str_hex(output, rdf); 788238104Sdes} 789238104Sdes 790238104Sdesldns_status 791238104Sdesldns_rdf2buffer_str_atma(ldns_buffer *output, const ldns_rdf *rdf) 792238104Sdes{ 793238104Sdes return ldns_rdf2buffer_str_hex(output, rdf); 794238104Sdes} 795238104Sdes 796238104Sdesldns_status 797238104Sdesldns_rdf2buffer_str_wks(ldns_buffer *output, const ldns_rdf *rdf) 798238104Sdes{ 799238104Sdes /* protocol, followed by bitmap of services */ 800238104Sdes struct protoent *protocol; 801238104Sdes char *proto_name = NULL; 802238104Sdes uint8_t protocol_nr; 803238104Sdes struct servent *service; 804238104Sdes uint16_t current_service; 805238104Sdes 806266114Sdes if(ldns_rdf_size(rdf) < 1) { 807266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 808266114Sdes } 809238104Sdes protocol_nr = ldns_rdf_data(rdf)[0]; 810238104Sdes protocol = getprotobynumber((int) protocol_nr); 811238104Sdes if (protocol && (protocol->p_name != NULL)) { 812238104Sdes proto_name = protocol->p_name; 813238104Sdes ldns_buffer_printf(output, "%s ", protocol->p_name); 814238104Sdes } else { 815238104Sdes ldns_buffer_printf(output, "%u ", protocol_nr); 816238104Sdes } 817238104Sdes 818238104Sdes#ifdef HAVE_ENDPROTOENT 819238104Sdes endprotoent(); 820238104Sdes#endif 821238104Sdes 822238104Sdes for (current_service = 0; 823238104Sdes current_service < ldns_rdf_size(rdf) * 7; current_service++) { 824238104Sdes if (ldns_get_bit(&(ldns_rdf_data(rdf)[1]), current_service)) { 825238104Sdes service = getservbyport((int) htons(current_service), 826238104Sdes proto_name); 827238104Sdes if (service && service->s_name) { 828238104Sdes ldns_buffer_printf(output, "%s ", service->s_name); 829238104Sdes } else { 830238104Sdes ldns_buffer_printf(output, "%u ", current_service); 831238104Sdes } 832238104Sdes#ifdef HAVE_ENDSERVENT 833238104Sdes endservent(); 834238104Sdes#endif 835238104Sdes } 836238104Sdes } 837238104Sdes return ldns_buffer_status(output); 838238104Sdes} 839238104Sdes 840266114Sdesstatic ldns_status 841266114Sdesldns_rdf2buffer_str_nsec_fmt(ldns_buffer *output, 842266114Sdes const ldns_output_format* fmt, const ldns_rdf *rdf) 843238104Sdes{ 844238104Sdes /* Note: this code is duplicated in higher.c in 845238104Sdes * ldns_nsec_type_check() function 846238104Sdes */ 847238104Sdes uint8_t window_block_nr; 848238104Sdes uint8_t bitmap_length; 849238104Sdes uint16_t type; 850238104Sdes uint16_t pos = 0; 851238104Sdes uint16_t bit_pos; 852238104Sdes uint8_t *data = ldns_rdf_data(rdf); 853238104Sdes 854266114Sdes while((size_t)(pos + 2) < ldns_rdf_size(rdf)) { 855238104Sdes window_block_nr = data[pos]; 856238104Sdes bitmap_length = data[pos + 1]; 857238104Sdes pos += 2; 858266114Sdes if (ldns_rdf_size(rdf) < pos + bitmap_length) { 859266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 860266114Sdes } 861238104Sdes for (bit_pos = 0; bit_pos < (bitmap_length) * 8; bit_pos++) { 862266114Sdes if (! ldns_get_bit(&data[pos], bit_pos)) { 863266114Sdes continue; 864266114Sdes } 865266114Sdes type = 256 * (uint16_t) window_block_nr + bit_pos; 866238104Sdes 867266114Sdes if (! ldns_output_format_covers_type(fmt, type) && 868266114Sdes ldns_rr_descript(type) && 869266114Sdes ldns_rr_descript(type)->_name){ 870266114Sdes 871266114Sdes ldns_buffer_printf(output, "%s ", 872266114Sdes ldns_rr_descript(type)->_name); 873266114Sdes } else { 874266114Sdes ldns_buffer_printf(output, "TYPE%u ", type); 875238104Sdes } 876238104Sdes } 877238104Sdes pos += (uint16_t) bitmap_length; 878238104Sdes } 879238104Sdes return ldns_buffer_status(output); 880238104Sdes} 881238104Sdes 882238104Sdesldns_status 883266114Sdesldns_rdf2buffer_str_nsec(ldns_buffer *output, const ldns_rdf *rdf) 884266114Sdes{ 885266114Sdes return ldns_rdf2buffer_str_nsec_fmt(output, 886266114Sdes ldns_output_format_default, rdf); 887266114Sdes} 888266114Sdes 889266114Sdesldns_status 890238104Sdesldns_rdf2buffer_str_nsec3_salt(ldns_buffer *output, const ldns_rdf *rdf) 891238104Sdes{ 892238104Sdes uint8_t salt_length; 893238104Sdes uint8_t salt_pos; 894238104Sdes 895238104Sdes uint8_t *data = ldns_rdf_data(rdf); 896238104Sdes 897266114Sdes if(ldns_rdf_size(rdf) < 1) { 898266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 899238104Sdes } 900238104Sdes salt_length = data[0]; 901238104Sdes /* from now there are variable length entries so remember pos */ 902238104Sdes if (salt_length == 0 || ((size_t)salt_length)+1 > ldns_rdf_size(rdf)) { 903238104Sdes ldns_buffer_printf(output, "- "); 904238104Sdes } else { 905238104Sdes for (salt_pos = 0; salt_pos < salt_length; salt_pos++) { 906238104Sdes ldns_buffer_printf(output, "%02x", data[1 + salt_pos]); 907238104Sdes } 908238104Sdes ldns_buffer_printf(output, " "); 909238104Sdes } 910238104Sdes 911238104Sdes return ldns_buffer_status(output); 912238104Sdes} 913238104Sdes 914238104Sdesldns_status 915238104Sdesldns_rdf2buffer_str_period(ldns_buffer *output, const ldns_rdf *rdf) 916238104Sdes{ 917238104Sdes /* period is the number of seconds */ 918266114Sdes if (ldns_rdf_size(rdf) != 4) { 919266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 920266114Sdes } 921266114Sdes ldns_buffer_printf(output, "%u", ldns_read_uint32(ldns_rdf_data(rdf))); 922238104Sdes return ldns_buffer_status(output); 923238104Sdes} 924238104Sdes 925238104Sdesldns_status 926238104Sdesldns_rdf2buffer_str_tsigtime(ldns_buffer *output,const ldns_rdf *rdf) 927238104Sdes{ 928238104Sdes /* tsigtime is 48 bits network order unsigned integer */ 929238104Sdes uint64_t tsigtime = 0; 930238104Sdes uint8_t *data = ldns_rdf_data(rdf); 931266114Sdes uint64_t d0, d1, d2, d3, d4, d5; 932238104Sdes 933266114Sdes if (ldns_rdf_size(rdf) < 6) { 934266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 935238104Sdes } 936266114Sdes d0 = data[0]; /* cast to uint64 for shift operations */ 937266114Sdes d1 = data[1]; 938266114Sdes d2 = data[2]; 939266114Sdes d3 = data[3]; 940266114Sdes d4 = data[4]; 941266114Sdes d5 = data[5]; 942266114Sdes tsigtime = (d0<<40) | (d1<<32) | (d2<<24) | (d3<<16) | (d4<<8) | d5; 943238104Sdes 944266114Sdes ldns_buffer_printf(output, "%llu ", (long long)tsigtime); 945238104Sdes 946238104Sdes return ldns_buffer_status(output); 947238104Sdes} 948238104Sdes 949238104Sdesldns_status 950238104Sdesldns_rdf2buffer_str_apl(ldns_buffer *output, const ldns_rdf *rdf) 951238104Sdes{ 952238104Sdes uint8_t *data = ldns_rdf_data(rdf); 953238104Sdes uint16_t address_family; 954238104Sdes uint8_t prefix; 955238104Sdes bool negation; 956238104Sdes uint8_t adf_length; 957238104Sdes size_t i; 958238104Sdes size_t pos = 0; 959238104Sdes 960238104Sdes while (pos < (unsigned int) ldns_rdf_size(rdf)) { 961238104Sdes if(pos + 3 >= (unsigned)ldns_rdf_size(rdf)) 962266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 963238104Sdes address_family = ldns_read_uint16(&data[pos]); 964238104Sdes prefix = data[pos + 2]; 965238104Sdes negation = data[pos + 3] & LDNS_APL_NEGATION; 966238104Sdes adf_length = data[pos + 3] & LDNS_APL_MASK; 967238104Sdes if (address_family == LDNS_APL_IP4) { 968238104Sdes /* check if prefix < 32? */ 969238104Sdes if (negation) { 970238104Sdes ldns_buffer_printf(output, "!"); 971238104Sdes } 972238104Sdes ldns_buffer_printf(output, "%u:", address_family); 973238104Sdes /* address is variable length 0 - 4 */ 974238104Sdes for (i = 0; i < 4; i++) { 975238104Sdes if (i > 0) { 976238104Sdes ldns_buffer_printf(output, "."); 977238104Sdes } 978238104Sdes if (i < (unsigned short) adf_length) { 979238104Sdes if(pos+i+4 >= ldns_rdf_size(rdf)) 980266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 981238104Sdes ldns_buffer_printf(output, "%d", 982238104Sdes data[pos + i + 4]); 983238104Sdes } else { 984238104Sdes ldns_buffer_printf(output, "0"); 985238104Sdes } 986238104Sdes } 987238104Sdes ldns_buffer_printf(output, "/%u ", prefix); 988238104Sdes } else if (address_family == LDNS_APL_IP6) { 989238104Sdes /* check if prefix < 128? */ 990238104Sdes if (negation) { 991238104Sdes ldns_buffer_printf(output, "!"); 992238104Sdes } 993238104Sdes ldns_buffer_printf(output, "%u:", address_family); 994238104Sdes /* address is variable length 0 - 16 */ 995238104Sdes for (i = 0; i < 16; i++) { 996238104Sdes if (i % 2 == 0 && i > 0) { 997238104Sdes ldns_buffer_printf(output, ":"); 998238104Sdes } 999238104Sdes if (i < (unsigned short) adf_length) { 1000238104Sdes if(pos+i+4 >= ldns_rdf_size(rdf)) 1001266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1002238104Sdes ldns_buffer_printf(output, "%02x", 1003238104Sdes data[pos + i + 4]); 1004238104Sdes } else { 1005238104Sdes ldns_buffer_printf(output, "00"); 1006238104Sdes } 1007238104Sdes } 1008238104Sdes ldns_buffer_printf(output, "/%u ", prefix); 1009238104Sdes 1010238104Sdes } else { 1011238104Sdes /* unknown address family */ 1012266114Sdes ldns_buffer_printf(output, 1013266114Sdes "Unknown address family: %u data: ", 1014238104Sdes address_family); 1015238104Sdes for (i = 1; i < (unsigned short) (4 + adf_length); i++) { 1016238104Sdes if(pos+i >= ldns_rdf_size(rdf)) 1017266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1018238104Sdes ldns_buffer_printf(output, "%02x", data[i]); 1019238104Sdes } 1020238104Sdes } 1021238104Sdes pos += 4 + adf_length; 1022238104Sdes } 1023238104Sdes return ldns_buffer_status(output); 1024238104Sdes} 1025238104Sdes 1026238104Sdesldns_status 1027238104Sdesldns_rdf2buffer_str_int16_data(ldns_buffer *output, const ldns_rdf *rdf) 1028238104Sdes{ 1029266114Sdes size_t size; 1030266114Sdes char *b64; 1031266114Sdes if (ldns_rdf_size(rdf) < 2) { 1032266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1033266114Sdes } 1034238104Sdes /* Subtract the size (2) of the number that specifies the length */ 1035266114Sdes size = ldns_b64_ntop_calculate_size(ldns_rdf_size(rdf) - 2); 1036238104Sdes ldns_buffer_printf(output, "%u ", ldns_rdf_size(rdf) - 2); 1037266114Sdes if (ldns_rdf_size(rdf) > 2) { 1038266114Sdes b64 = LDNS_XMALLOC(char, size); 1039266114Sdes if(!b64) 1040266114Sdes return LDNS_STATUS_MEM_ERR; 1041238104Sdes 1042266114Sdes if (ldns_rdf_size(rdf) > 2 && 1043266114Sdes ldns_b64_ntop(ldns_rdf_data(rdf) + 2, 1044266114Sdes ldns_rdf_size(rdf) - 2, 1045266114Sdes b64, size)) { 1046266114Sdes ldns_buffer_printf(output, "%s", b64); 1047266114Sdes } 1048266114Sdes LDNS_FREE(b64); 1049238104Sdes } 1050238104Sdes return ldns_buffer_status(output); 1051238104Sdes} 1052238104Sdes 1053238104Sdesldns_status 1054238104Sdesldns_rdf2buffer_str_ipseckey(ldns_buffer *output, const ldns_rdf *rdf) 1055238104Sdes{ 1056238104Sdes /* wire format from 1057238104Sdes http://www.ietf.org/internet-drafts/draft-ietf-ipseckey-rr-12.txt 1058238104Sdes */ 1059238104Sdes uint8_t *data = ldns_rdf_data(rdf); 1060238104Sdes uint8_t precedence; 1061238104Sdes uint8_t gateway_type; 1062238104Sdes uint8_t algorithm; 1063238104Sdes 1064238104Sdes ldns_rdf *gateway = NULL; 1065238104Sdes uint8_t *gateway_data; 1066238104Sdes 1067238104Sdes size_t public_key_size; 1068238104Sdes uint8_t *public_key_data; 1069238104Sdes ldns_rdf *public_key; 1070238104Sdes 1071238104Sdes size_t offset = 0; 1072238104Sdes ldns_status status; 1073238104Sdes 1074266114Sdes if (ldns_rdf_size(rdf) < 3) { 1075266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1076266114Sdes } 1077238104Sdes precedence = data[0]; 1078238104Sdes gateway_type = data[1]; 1079238104Sdes algorithm = data[2]; 1080238104Sdes offset = 3; 1081238104Sdes 1082238104Sdes switch (gateway_type) { 1083238104Sdes case 0: 1084238104Sdes /* no gateway */ 1085238104Sdes break; 1086238104Sdes case 1: 1087238104Sdes gateway_data = LDNS_XMALLOC(uint8_t, LDNS_IP4ADDRLEN); 1088238104Sdes if(!gateway_data) 1089238104Sdes return LDNS_STATUS_MEM_ERR; 1090266114Sdes if (ldns_rdf_size(rdf) < offset + LDNS_IP4ADDRLEN) { 1091266114Sdes return LDNS_STATUS_ERR; 1092266114Sdes } 1093238104Sdes memcpy(gateway_data, &data[offset], LDNS_IP4ADDRLEN); 1094266114Sdes gateway = ldns_rdf_new(LDNS_RDF_TYPE_A, 1095266114Sdes LDNS_IP4ADDRLEN , gateway_data); 1096238104Sdes offset += LDNS_IP4ADDRLEN; 1097238104Sdes if(!gateway) { 1098238104Sdes LDNS_FREE(gateway_data); 1099238104Sdes return LDNS_STATUS_MEM_ERR; 1100238104Sdes } 1101238104Sdes break; 1102238104Sdes case 2: 1103238104Sdes gateway_data = LDNS_XMALLOC(uint8_t, LDNS_IP6ADDRLEN); 1104238104Sdes if(!gateway_data) 1105238104Sdes return LDNS_STATUS_MEM_ERR; 1106266114Sdes if (ldns_rdf_size(rdf) < offset + LDNS_IP6ADDRLEN) { 1107266114Sdes return LDNS_STATUS_ERR; 1108266114Sdes } 1109238104Sdes memcpy(gateway_data, &data[offset], LDNS_IP6ADDRLEN); 1110238104Sdes offset += LDNS_IP6ADDRLEN; 1111238104Sdes gateway = 1112266114Sdes ldns_rdf_new(LDNS_RDF_TYPE_AAAA, 1113266114Sdes LDNS_IP6ADDRLEN, gateway_data); 1114238104Sdes if(!gateway) { 1115238104Sdes LDNS_FREE(gateway_data); 1116238104Sdes return LDNS_STATUS_MEM_ERR; 1117238104Sdes } 1118238104Sdes break; 1119238104Sdes case 3: 1120266114Sdes status = ldns_wire2dname(&gateway, data, 1121266114Sdes ldns_rdf_size(rdf), &offset); 1122238104Sdes if(status != LDNS_STATUS_OK) 1123238104Sdes return status; 1124238104Sdes break; 1125238104Sdes default: 1126238104Sdes /* error? */ 1127238104Sdes break; 1128238104Sdes } 1129238104Sdes 1130266114Sdes if (ldns_rdf_size(rdf) <= offset) { 1131266114Sdes return LDNS_STATUS_ERR; 1132266114Sdes } 1133238104Sdes public_key_size = ldns_rdf_size(rdf) - offset; 1134238104Sdes public_key_data = LDNS_XMALLOC(uint8_t, public_key_size); 1135238104Sdes if(!public_key_data) { 1136238104Sdes ldns_rdf_free(gateway); 1137238104Sdes return LDNS_STATUS_MEM_ERR; 1138238104Sdes } 1139238104Sdes memcpy(public_key_data, &data[offset], public_key_size); 1140266114Sdes public_key = ldns_rdf_new(LDNS_RDF_TYPE_B64, 1141266114Sdes public_key_size, public_key_data); 1142238104Sdes if(!public_key) { 1143238104Sdes LDNS_FREE(public_key_data); 1144238104Sdes ldns_rdf_free(gateway); 1145238104Sdes return LDNS_STATUS_MEM_ERR; 1146238104Sdes } 1147238104Sdes 1148238104Sdes ldns_buffer_printf(output, "%u %u %u ", precedence, gateway_type, algorithm); 1149266114Sdes if (gateway) 1150238104Sdes (void) ldns_rdf2buffer_str(output, gateway); 1151238104Sdes else 1152238104Sdes ldns_buffer_printf(output, "."); 1153238104Sdes ldns_buffer_printf(output, " "); 1154238104Sdes (void) ldns_rdf2buffer_str(output, public_key); 1155238104Sdes 1156238104Sdes ldns_rdf_free(gateway); 1157238104Sdes ldns_rdf_free(public_key); 1158238104Sdes 1159238104Sdes return ldns_buffer_status(output); 1160238104Sdes} 1161238104Sdes 1162238104Sdesldns_status 1163266114Sdesldns_rdf2buffer_str_ilnp64(ldns_buffer *output, const ldns_rdf *rdf) 1164238104Sdes{ 1165266114Sdes if (ldns_rdf_size(rdf) != 8) { 1166266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1167266114Sdes } 1168266114Sdes ldns_buffer_printf(output,"%.4x:%.4x:%.4x:%.4x", 1169266114Sdes ldns_read_uint16(ldns_rdf_data(rdf)), 1170266114Sdes ldns_read_uint16(ldns_rdf_data(rdf)+2), 1171266114Sdes ldns_read_uint16(ldns_rdf_data(rdf)+4), 1172266114Sdes ldns_read_uint16(ldns_rdf_data(rdf)+6)); 1173266114Sdes return ldns_buffer_status(output); 1174238104Sdes} 1175238104Sdes 1176266114Sdesldns_status 1177266114Sdesldns_rdf2buffer_str_eui48(ldns_buffer *output, const ldns_rdf *rdf) 1178266114Sdes{ 1179266114Sdes if (ldns_rdf_size(rdf) != 6) { 1180266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1181266114Sdes } 1182266114Sdes ldns_buffer_printf(output,"%.2x-%.2x-%.2x-%.2x-%.2x-%.2x", 1183266114Sdes ldns_rdf_data(rdf)[0], ldns_rdf_data(rdf)[1], 1184266114Sdes ldns_rdf_data(rdf)[2], ldns_rdf_data(rdf)[3], 1185266114Sdes ldns_rdf_data(rdf)[4], ldns_rdf_data(rdf)[5]); 1186266114Sdes return ldns_buffer_status(output); 1187266114Sdes} 1188238104Sdes 1189238104Sdesldns_status 1190266114Sdesldns_rdf2buffer_str_eui64(ldns_buffer *output, const ldns_rdf *rdf) 1191238104Sdes{ 1192266114Sdes if (ldns_rdf_size(rdf) != 8) { 1193266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1194266114Sdes } 1195266114Sdes ldns_buffer_printf(output,"%.2x-%.2x-%.2x-%.2x-%.2x-%.2x-%.2x-%.2x", 1196266114Sdes ldns_rdf_data(rdf)[0], ldns_rdf_data(rdf)[1], 1197266114Sdes ldns_rdf_data(rdf)[2], ldns_rdf_data(rdf)[3], 1198266114Sdes ldns_rdf_data(rdf)[4], ldns_rdf_data(rdf)[5], 1199266114Sdes ldns_rdf_data(rdf)[6], ldns_rdf_data(rdf)[7]); 1200266114Sdes return ldns_buffer_status(output); 1201266114Sdes} 1202266114Sdes 1203266114Sdesldns_status 1204266114Sdesldns_rdf2buffer_str_tag(ldns_buffer *output, const ldns_rdf *rdf) 1205266114Sdes{ 1206266114Sdes size_t nchars; 1207266114Sdes const uint8_t* chars; 1208266114Sdes char ch; 1209266114Sdes if (ldns_rdf_size(rdf) < 2) { 1210266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1211266114Sdes } 1212266114Sdes nchars = ldns_rdf_data(rdf)[0]; 1213266114Sdes if (nchars >= ldns_rdf_size(rdf) || /* should be rdf_size - 1 */ 1214266114Sdes nchars < 1) { 1215266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1216266114Sdes } 1217266114Sdes chars = ldns_rdf_data(rdf) + 1; 1218266114Sdes while (nchars > 0) { 1219266114Sdes ch = (char)*chars++; 1220266114Sdes if (! isalnum(ch)) { 1221266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1222266114Sdes } 1223266114Sdes ldns_buffer_printf(output, "%c", ch); 1224266114Sdes nchars--; 1225266114Sdes } 1226266114Sdes return ldns_buffer_status(output); 1227266114Sdes} 1228266114Sdes 1229266114Sdesldns_status 1230266114Sdesldns_rdf2buffer_str_long_str(ldns_buffer *output, const ldns_rdf *rdf) 1231266114Sdes{ 1232266114Sdes 1233266114Sdes ldns_buffer_printf(output, "\""); 1234266114Sdes ldns_characters2buffer_str(output, 1235266114Sdes ldns_rdf_size(rdf), ldns_rdf_data(rdf)); 1236266114Sdes ldns_buffer_printf(output, "\""); 1237266114Sdes return ldns_buffer_status(output); 1238266114Sdes} 1239266114Sdes 1240266114Sdesldns_status 1241266114Sdesldns_rdf2buffer_str_hip(ldns_buffer *output, const ldns_rdf *rdf) 1242266114Sdes{ 1243266114Sdes uint8_t *data = ldns_rdf_data(rdf); 1244266114Sdes size_t rdf_size = ldns_rdf_size(rdf); 1245266114Sdes uint8_t hit_size; 1246266114Sdes uint16_t pk_size; 1247266114Sdes int written; 1248266114Sdes 1249266114Sdes if (rdf_size < 6) { 1250266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1251266114Sdes } 1252266114Sdes if ((hit_size = data[0]) == 0 || 1253266114Sdes (pk_size = ldns_read_uint16(data + 2)) == 0 || 1254266114Sdes rdf_size < (size_t) hit_size + pk_size + 4) { 1255266114Sdes 1256266114Sdes return LDNS_STATUS_WIRE_RDATA_ERR; 1257266114Sdes } 1258266114Sdes 1259266114Sdes ldns_buffer_printf(output, "%d ", (int) data[1]); 1260266114Sdes 1261266114Sdes for (data += 4; hit_size > 0; hit_size--, data++) { 1262266114Sdes 1263266114Sdes ldns_buffer_printf(output, "%02x", (int) *data); 1264266114Sdes } 1265266114Sdes ldns_buffer_write_u8(output, (uint8_t) ' '); 1266266114Sdes 1267266114Sdes if (ldns_buffer_reserve(output, 1268266114Sdes ldns_b64_ntop_calculate_size(pk_size))) { 1269266114Sdes 1270266114Sdes written = ldns_b64_ntop(data, pk_size, 1271266114Sdes (char *) ldns_buffer_current(output), 1272266114Sdes ldns_buffer_remaining(output)); 1273266114Sdes 1274266114Sdes if (written > 0 && 1275266114Sdes written < (int) ldns_buffer_remaining(output)) { 1276266114Sdes 1277266114Sdes output->_position += written; 1278266114Sdes } 1279266114Sdes } 1280266114Sdes return ldns_buffer_status(output); 1281266114Sdes} 1282266114Sdes 1283266114Sdesstatic ldns_status 1284266114Sdesldns_rdf2buffer_str_fmt(ldns_buffer *buffer, 1285266114Sdes const ldns_output_format* fmt, const ldns_rdf *rdf) 1286266114Sdes{ 1287238104Sdes ldns_status res = LDNS_STATUS_OK; 1288238104Sdes 1289238104Sdes /*ldns_buffer_printf(buffer, "%u:", ldns_rdf_get_type(rdf));*/ 1290238104Sdes if (rdf) { 1291238104Sdes switch(ldns_rdf_get_type(rdf)) { 1292238104Sdes case LDNS_RDF_TYPE_NONE: 1293238104Sdes break; 1294238104Sdes case LDNS_RDF_TYPE_DNAME: 1295238104Sdes res = ldns_rdf2buffer_str_dname(buffer, rdf); 1296238104Sdes break; 1297238104Sdes case LDNS_RDF_TYPE_INT8: 1298238104Sdes res = ldns_rdf2buffer_str_int8(buffer, rdf); 1299238104Sdes break; 1300238104Sdes case LDNS_RDF_TYPE_INT16: 1301238104Sdes res = ldns_rdf2buffer_str_int16(buffer, rdf); 1302238104Sdes break; 1303238104Sdes case LDNS_RDF_TYPE_INT32: 1304238104Sdes res = ldns_rdf2buffer_str_int32(buffer, rdf); 1305238104Sdes break; 1306238104Sdes case LDNS_RDF_TYPE_PERIOD: 1307238104Sdes res = ldns_rdf2buffer_str_period(buffer, rdf); 1308238104Sdes break; 1309238104Sdes case LDNS_RDF_TYPE_TSIGTIME: 1310238104Sdes res = ldns_rdf2buffer_str_tsigtime(buffer, rdf); 1311238104Sdes break; 1312238104Sdes case LDNS_RDF_TYPE_A: 1313238104Sdes res = ldns_rdf2buffer_str_a(buffer, rdf); 1314238104Sdes break; 1315238104Sdes case LDNS_RDF_TYPE_AAAA: 1316238104Sdes res = ldns_rdf2buffer_str_aaaa(buffer, rdf); 1317238104Sdes break; 1318238104Sdes case LDNS_RDF_TYPE_STR: 1319238104Sdes res = ldns_rdf2buffer_str_str(buffer, rdf); 1320238104Sdes break; 1321238104Sdes case LDNS_RDF_TYPE_APL: 1322238104Sdes res = ldns_rdf2buffer_str_apl(buffer, rdf); 1323238104Sdes break; 1324238104Sdes case LDNS_RDF_TYPE_B32_EXT: 1325238104Sdes res = ldns_rdf2buffer_str_b32_ext(buffer, rdf); 1326238104Sdes break; 1327238104Sdes case LDNS_RDF_TYPE_B64: 1328238104Sdes res = ldns_rdf2buffer_str_b64(buffer, rdf); 1329238104Sdes break; 1330238104Sdes case LDNS_RDF_TYPE_HEX: 1331238104Sdes res = ldns_rdf2buffer_str_hex(buffer, rdf); 1332238104Sdes break; 1333238104Sdes case LDNS_RDF_TYPE_NSEC: 1334266114Sdes res = ldns_rdf2buffer_str_nsec_fmt(buffer, fmt, rdf); 1335238104Sdes break; 1336238104Sdes case LDNS_RDF_TYPE_NSEC3_SALT: 1337238104Sdes res = ldns_rdf2buffer_str_nsec3_salt(buffer, rdf); 1338238104Sdes break; 1339238104Sdes case LDNS_RDF_TYPE_TYPE: 1340266114Sdes res = ldns_rdf2buffer_str_type_fmt(buffer, fmt, rdf); 1341238104Sdes break; 1342238104Sdes case LDNS_RDF_TYPE_CLASS: 1343238104Sdes res = ldns_rdf2buffer_str_class(buffer, rdf); 1344238104Sdes break; 1345238104Sdes case LDNS_RDF_TYPE_CERT_ALG: 1346238104Sdes res = ldns_rdf2buffer_str_cert_alg(buffer, rdf); 1347238104Sdes break; 1348238104Sdes case LDNS_RDF_TYPE_ALG: 1349238104Sdes res = ldns_rdf2buffer_str_alg(buffer, rdf); 1350238104Sdes break; 1351238104Sdes case LDNS_RDF_TYPE_UNKNOWN: 1352238104Sdes res = ldns_rdf2buffer_str_unknown(buffer, rdf); 1353238104Sdes break; 1354238104Sdes case LDNS_RDF_TYPE_TIME: 1355238104Sdes res = ldns_rdf2buffer_str_time(buffer, rdf); 1356238104Sdes break; 1357266114Sdes case LDNS_RDF_TYPE_HIP: 1358266114Sdes res = ldns_rdf2buffer_str_hip(buffer, rdf); 1359266114Sdes break; 1360238104Sdes case LDNS_RDF_TYPE_LOC: 1361238104Sdes res = ldns_rdf2buffer_str_loc(buffer, rdf); 1362238104Sdes break; 1363238104Sdes case LDNS_RDF_TYPE_WKS: 1364238104Sdes case LDNS_RDF_TYPE_SERVICE: 1365238104Sdes res = ldns_rdf2buffer_str_wks(buffer, rdf); 1366238104Sdes break; 1367238104Sdes case LDNS_RDF_TYPE_NSAP: 1368238104Sdes res = ldns_rdf2buffer_str_nsap(buffer, rdf); 1369238104Sdes break; 1370238104Sdes case LDNS_RDF_TYPE_ATMA: 1371238104Sdes res = ldns_rdf2buffer_str_atma(buffer, rdf); 1372238104Sdes break; 1373238104Sdes case LDNS_RDF_TYPE_IPSECKEY: 1374238104Sdes res = ldns_rdf2buffer_str_ipseckey(buffer, rdf); 1375238104Sdes break; 1376238104Sdes case LDNS_RDF_TYPE_INT16_DATA: 1377238104Sdes res = ldns_rdf2buffer_str_int16_data(buffer, rdf); 1378238104Sdes break; 1379238104Sdes case LDNS_RDF_TYPE_NSEC3_NEXT_OWNER: 1380238104Sdes res = ldns_rdf2buffer_str_b32_ext(buffer, rdf); 1381238104Sdes break; 1382266114Sdes case LDNS_RDF_TYPE_ILNP64: 1383266114Sdes res = ldns_rdf2buffer_str_ilnp64(buffer, rdf); 1384266114Sdes break; 1385266114Sdes case LDNS_RDF_TYPE_EUI48: 1386266114Sdes res = ldns_rdf2buffer_str_eui48(buffer, rdf); 1387266114Sdes break; 1388266114Sdes case LDNS_RDF_TYPE_EUI64: 1389266114Sdes res = ldns_rdf2buffer_str_eui64(buffer, rdf); 1390266114Sdes break; 1391266114Sdes case LDNS_RDF_TYPE_TAG: 1392266114Sdes res = ldns_rdf2buffer_str_tag(buffer, rdf); 1393266114Sdes break; 1394266114Sdes case LDNS_RDF_TYPE_LONG_STR: 1395266114Sdes res = ldns_rdf2buffer_str_long_str(buffer, rdf); 1396266114Sdes break; 1397238104Sdes } 1398238104Sdes } else { 1399246854Sdes /** This will write mangled RRs */ 1400238104Sdes ldns_buffer_printf(buffer, "(null) "); 1401246854Sdes res = LDNS_STATUS_ERR; 1402238104Sdes } 1403238104Sdes return res; 1404238104Sdes} 1405238104Sdes 1406266114Sdesldns_status 1407266114Sdesldns_rdf2buffer_str(ldns_buffer *buffer, const ldns_rdf *rdf) 1408266114Sdes{ 1409266114Sdes return ldns_rdf2buffer_str_fmt(buffer,ldns_output_format_default,rdf); 1410266114Sdes} 1411266114Sdes 1412246827Sdesstatic ldns_rdf * 1413238104Sdesldns_b32_ext2dname(const ldns_rdf *rdf) 1414238104Sdes{ 1415238104Sdes size_t size; 1416238104Sdes char *b32; 1417238104Sdes ldns_rdf *out; 1418238104Sdes if(ldns_rdf_size(rdf) == 0) 1419238104Sdes return NULL; 1420238104Sdes /* remove -1 for the b32-hash-len octet */ 1421238104Sdes size = ldns_b32_ntop_calculate_size(ldns_rdf_size(rdf) - 1); 1422238104Sdes /* add one for the end nul for the string */ 1423238104Sdes b32 = LDNS_XMALLOC(char, size + 2); 1424238104Sdes if (b32) { 1425238104Sdes if (ldns_b32_ntop_extended_hex(ldns_rdf_data(rdf) + 1, 1426238104Sdes ldns_rdf_size(rdf) - 1, b32, size+1) > 0) { 1427238104Sdes b32[size] = '.'; 1428238104Sdes b32[size+1] = '\0'; 1429238104Sdes if (ldns_str2rdf_dname(&out, b32) == LDNS_STATUS_OK) { 1430238104Sdes LDNS_FREE(b32); 1431238104Sdes return out; 1432238104Sdes } 1433238104Sdes } 1434238104Sdes LDNS_FREE(b32); 1435238104Sdes } 1436238104Sdes return NULL; 1437238104Sdes} 1438238104Sdes 1439266114Sdesstatic ldns_status 1440266114Sdesldns_rr2buffer_str_rfc3597(ldns_buffer *output, const ldns_rr *rr) 1441266114Sdes{ 1442266114Sdes size_t total_rdfsize = 0; 1443266114Sdes size_t i, j; 1444266114Sdes 1445266114Sdes ldns_buffer_printf(output, "TYPE%u\t", ldns_rr_get_type(rr)); 1446266114Sdes for (i = 0; i < ldns_rr_rd_count(rr); i++) { 1447266114Sdes total_rdfsize += ldns_rdf_size(ldns_rr_rdf(rr, i)); 1448266114Sdes } 1449266114Sdes if (total_rdfsize == 0) { 1450266114Sdes ldns_buffer_printf(output, "\\# 0\n"); 1451266114Sdes return ldns_buffer_status(output); 1452266114Sdes } 1453266114Sdes ldns_buffer_printf(output, "\\# %d ", total_rdfsize); 1454266114Sdes for (i = 0; i < ldns_rr_rd_count(rr); i++) { 1455266114Sdes for (j = 0; j < ldns_rdf_size(ldns_rr_rdf(rr, i)); j++) { 1456266114Sdes ldns_buffer_printf(output, "%.2x", 1457266114Sdes ldns_rdf_data(ldns_rr_rdf(rr, i))[j]); 1458266114Sdes } 1459266114Sdes } 1460266114Sdes ldns_buffer_printf(output, "\n"); 1461266114Sdes return ldns_buffer_status(output); 1462266114Sdes} 1463266114Sdes 1464238104Sdesldns_status 1465238104Sdesldns_rr2buffer_str_fmt(ldns_buffer *output, 1466238104Sdes const ldns_output_format *fmt, const ldns_rr *rr) 1467238104Sdes{ 1468238104Sdes uint16_t i, flags; 1469238104Sdes ldns_status status = LDNS_STATUS_OK; 1470266114Sdes ldns_output_format_storage* fmt_st = (ldns_output_format_storage*)fmt; 1471238104Sdes 1472266114Sdes if (fmt_st == NULL) { 1473266114Sdes fmt_st = (ldns_output_format_storage*) 1474266114Sdes ldns_output_format_default; 1475238104Sdes } 1476238104Sdes if (!rr) { 1477266114Sdes if (LDNS_COMMENT_NULLS & fmt_st->flags) { 1478238104Sdes ldns_buffer_printf(output, "; (null)\n"); 1479238104Sdes } 1480238104Sdes return ldns_buffer_status(output); 1481238104Sdes } 1482238104Sdes if (ldns_rr_owner(rr)) { 1483238104Sdes status = ldns_rdf2buffer_str_dname(output, ldns_rr_owner(rr)); 1484238104Sdes } 1485238104Sdes if (status != LDNS_STATUS_OK) { 1486238104Sdes return status; 1487238104Sdes } 1488238104Sdes 1489238104Sdes /* TTL should NOT be printed if it is a question */ 1490238104Sdes if (!ldns_rr_is_question(rr)) { 1491238104Sdes ldns_buffer_printf(output, "\t%d", ldns_rr_ttl(rr)); 1492238104Sdes } 1493238104Sdes 1494238104Sdes ldns_buffer_printf(output, "\t"); 1495238104Sdes status = ldns_rr_class2buffer_str(output, ldns_rr_get_class(rr)); 1496238104Sdes if (status != LDNS_STATUS_OK) { 1497238104Sdes return status; 1498238104Sdes } 1499238104Sdes ldns_buffer_printf(output, "\t"); 1500238104Sdes 1501266114Sdes if (ldns_output_format_covers_type(fmt, ldns_rr_get_type(rr))) { 1502266114Sdes return ldns_rr2buffer_str_rfc3597(output, rr); 1503266114Sdes } 1504238104Sdes status = ldns_rr_type2buffer_str(output, ldns_rr_get_type(rr)); 1505238104Sdes if (status != LDNS_STATUS_OK) { 1506238104Sdes return status; 1507238104Sdes } 1508238104Sdes 1509238104Sdes if (ldns_rr_rd_count(rr) > 0) { 1510238104Sdes ldns_buffer_printf(output, "\t"); 1511238104Sdes } else if (!ldns_rr_is_question(rr)) { 1512238104Sdes ldns_buffer_printf(output, "\t\\# 0"); 1513238104Sdes } 1514238104Sdes 1515238104Sdes for (i = 0; i < ldns_rr_rd_count(rr); i++) { 1516238104Sdes /* ldns_rdf2buffer_str handles NULL input fine! */ 1517266114Sdes if ((fmt_st->flags & LDNS_FMT_ZEROIZE_RRSIGS) && 1518246854Sdes (ldns_rr_get_type(rr) == LDNS_RR_TYPE_RRSIG) && 1519246854Sdes ((/* inception */ i == 4 && 1520246854Sdes ldns_rdf_get_type(ldns_rr_rdf(rr, 4)) == 1521246854Sdes LDNS_RDF_TYPE_TIME) || 1522246854Sdes (/* expiration */ i == 5 && 1523246854Sdes ldns_rdf_get_type(ldns_rr_rdf(rr, 5)) == 1524246854Sdes LDNS_RDF_TYPE_TIME) || 1525246854Sdes (/* signature */ i == 8 && 1526246854Sdes ldns_rdf_get_type(ldns_rr_rdf(rr, 8)) == 1527246854Sdes LDNS_RDF_TYPE_B64))) { 1528246854Sdes 1529246854Sdes ldns_buffer_printf(output, "(null)"); 1530246854Sdes status = ldns_buffer_status(output); 1531266114Sdes } else if ((fmt_st->flags & LDNS_FMT_PAD_SOA_SERIAL) && 1532246854Sdes (ldns_rr_get_type(rr) == LDNS_RR_TYPE_SOA) && 1533246854Sdes /* serial */ i == 2 && 1534246854Sdes ldns_rdf_get_type(ldns_rr_rdf(rr, 2)) == 1535246854Sdes LDNS_RDF_TYPE_INT32) { 1536246854Sdes ldns_buffer_printf(output, "%10lu", 1537246854Sdes (unsigned long) ldns_read_uint32( 1538246854Sdes ldns_rdf_data(ldns_rr_rdf(rr, 2)))); 1539246854Sdes status = ldns_buffer_status(output); 1540246854Sdes } else { 1541266114Sdes status = ldns_rdf2buffer_str_fmt(output, 1542266114Sdes fmt, ldns_rr_rdf(rr, i)); 1543246854Sdes } 1544238104Sdes if(status != LDNS_STATUS_OK) 1545238104Sdes return status; 1546238104Sdes if (i < ldns_rr_rd_count(rr) - 1) { 1547238104Sdes ldns_buffer_printf(output, " "); 1548238104Sdes } 1549238104Sdes } 1550238104Sdes /* per RR special comments - handy for DNSSEC types */ 1551238104Sdes /* check to prevent question sec. rr from 1552238104Sdes * getting here */ 1553238104Sdes if (ldns_rr_rd_count(rr) > 0) { 1554238104Sdes switch (ldns_rr_get_type(rr)) { 1555266114Sdes case LDNS_RR_TYPE_DNSKEY: 1556266114Sdes /* if ldns_rr_rd_count(rr) > 0 1557266114Sdes then ldns_rr_rdf(rr, 0) exists! */ 1558266114Sdes if (! (fmt_st->flags & LDNS_COMMENT_KEY)) { 1559266114Sdes break; 1560266114Sdes } 1561266114Sdes flags = ldns_rdf2native_int16(ldns_rr_rdf(rr, 0)); 1562266114Sdes ldns_buffer_printf(output, " ;{"); 1563266114Sdes if (fmt_st->flags & LDNS_COMMENT_KEY_ID) { 1564266114Sdes ldns_buffer_printf(output, "id = %u", 1565266114Sdes (unsigned int) ldns_calc_keytag(rr)); 1566266114Sdes } 1567266114Sdes if ((fmt_st->flags & LDNS_COMMENT_KEY_TYPE) && 1568266114Sdes (flags & LDNS_KEY_ZONE_KEY)){ 1569266114Sdes 1570266114Sdes if (flags & LDNS_KEY_SEP_KEY) { 1571266114Sdes ldns_buffer_printf(output, " (ksk)"); 1572266114Sdes } else { 1573266114Sdes ldns_buffer_printf(output, " (zsk)"); 1574238104Sdes } 1575266114Sdes if (fmt_st->flags & LDNS_COMMENT_KEY_SIZE){ 1576266114Sdes ldns_buffer_printf(output, ", "); 1577238104Sdes } 1578266114Sdes } else if (fmt_st->flags 1579266114Sdes & (LDNS_COMMENT_KEY_ID 1580266114Sdes |LDNS_COMMENT_KEY_SIZE)) { 1581266114Sdes ldns_buffer_printf( output, ", "); 1582266114Sdes } 1583266114Sdes if (fmt_st->flags & LDNS_COMMENT_KEY_SIZE) { 1584266114Sdes ldns_buffer_printf(output, "size = %db", 1585266114Sdes ldns_rr_dnskey_key_size(rr)); 1586266114Sdes } 1587266114Sdes ldns_buffer_printf(output, "}"); 1588266114Sdes break; 1589266114Sdes case LDNS_RR_TYPE_RRSIG: 1590266114Sdes if ((fmt_st->flags & LDNS_COMMENT_KEY) 1591266114Sdes && (fmt_st->flags& LDNS_COMMENT_RRSIGS) 1592266114Sdes && ldns_rr_rdf(rr, 6) != NULL) { 1593266114Sdes ldns_buffer_printf(output, " ;{id = %d}", 1594266114Sdes ldns_rdf2native_int16( 1595238104Sdes ldns_rr_rdf(rr, 6))); 1596266114Sdes } 1597266114Sdes break; 1598266114Sdes case LDNS_RR_TYPE_DS: 1599266114Sdes if ((fmt_st->flags & LDNS_COMMENT_BUBBLEBABBLE) && 1600266114Sdes ldns_rr_rdf(rr, 3) != NULL) { 1601266114Sdes 1602266114Sdes uint8_t *data = ldns_rdf_data( 1603266114Sdes ldns_rr_rdf(rr, 3)); 1604266114Sdes size_t len = ldns_rdf_size(ldns_rr_rdf(rr, 3)); 1605266114Sdes char *babble = ldns_bubblebabble(data, len); 1606266114Sdes if(babble) { 1607266114Sdes ldns_buffer_printf(output, 1608266114Sdes " ;{%s}", babble); 1609238104Sdes } 1610266114Sdes LDNS_FREE(babble); 1611266114Sdes } 1612266114Sdes break; 1613266114Sdes case LDNS_RR_TYPE_NSEC3: 1614266114Sdes if (! (fmt_st->flags & LDNS_COMMENT_FLAGS) && 1615266114Sdes ! (fmt_st->flags & LDNS_COMMENT_NSEC3_CHAIN)) { 1616238104Sdes break; 1617266114Sdes } 1618266114Sdes ldns_buffer_printf(output, " ;{"); 1619266114Sdes if ((fmt_st->flags & LDNS_COMMENT_FLAGS)) { 1620266114Sdes if (ldns_nsec3_optout(rr)) { 1621266114Sdes ldns_buffer_printf(output, 1622266114Sdes " flags: optout"); 1623266114Sdes } else { 1624266114Sdes ldns_buffer_printf(output," flags: -"); 1625238104Sdes } 1626266114Sdes if (fmt_st->flags & LDNS_COMMENT_NSEC3_CHAIN && 1627266114Sdes fmt_st->hashmap != NULL) { 1628266114Sdes ldns_buffer_printf(output, ", "); 1629238104Sdes } 1630266114Sdes } 1631266114Sdes if (fmt_st->flags & LDNS_COMMENT_NSEC3_CHAIN && 1632266114Sdes fmt_st->hashmap != NULL) { 1633266114Sdes ldns_rbnode_t *node; 1634266114Sdes ldns_rdf *key = ldns_dname_label( 1635266114Sdes ldns_rr_owner(rr), 0); 1636266114Sdes if (key) { 1637266114Sdes node = ldns_rbtree_search( 1638266114Sdes fmt_st->hashmap, 1639266114Sdes (void *) key); 1640266114Sdes if (node->data) { 1641238104Sdes ldns_buffer_printf(output, 1642266114Sdes "from: "); 1643266114Sdes (void) ldns_rdf2buffer_str( 1644266114Sdes output, 1645266114Sdes ldns_dnssec_name_name( 1646266114Sdes (ldns_dnssec_name*) 1647266114Sdes node->data 1648266114Sdes )); 1649238104Sdes } 1650266114Sdes ldns_rdf_free(key); 1651238104Sdes } 1652266114Sdes key = ldns_b32_ext2dname( 1653238104Sdes ldns_nsec3_next_owner(rr)); 1654266114Sdes if (key) { 1655266114Sdes node = ldns_rbtree_search( 1656266114Sdes fmt_st->hashmap, 1657266114Sdes (void *) key); 1658266114Sdes if (node->data) { 1659266114Sdes ldns_buffer_printf(output, 1660266114Sdes " to: "); 1661266114Sdes (void) ldns_rdf2buffer_str( 1662266114Sdes output, 1663266114Sdes ldns_dnssec_name_name( 1664266114Sdes (ldns_dnssec_name*) 1665266114Sdes node->data 1666266114Sdes )); 1667238104Sdes } 1668266114Sdes ldns_rdf_free(key); 1669238104Sdes } 1670266114Sdes } 1671266114Sdes ldns_buffer_printf(output, "}"); 1672266114Sdes break; 1673266114Sdes default: 1674266114Sdes break; 1675238104Sdes 1676238104Sdes } 1677238104Sdes } 1678238104Sdes /* last */ 1679238104Sdes ldns_buffer_printf(output, "\n"); 1680238104Sdes return ldns_buffer_status(output); 1681238104Sdes} 1682238104Sdes 1683238104Sdesldns_status 1684238104Sdesldns_rr2buffer_str(ldns_buffer *output, const ldns_rr *rr) 1685238104Sdes{ 1686238104Sdes return ldns_rr2buffer_str_fmt(output, ldns_output_format_default, rr); 1687238104Sdes} 1688238104Sdes 1689238104Sdesldns_status 1690238104Sdesldns_rr_list2buffer_str_fmt(ldns_buffer *output, 1691238104Sdes const ldns_output_format *fmt, const ldns_rr_list *list) 1692238104Sdes{ 1693238104Sdes uint16_t i; 1694238104Sdes 1695238104Sdes for(i = 0; i < ldns_rr_list_rr_count(list); i++) { 1696238104Sdes (void) ldns_rr2buffer_str_fmt(output, fmt, 1697238104Sdes ldns_rr_list_rr(list, i)); 1698238104Sdes } 1699238104Sdes return ldns_buffer_status(output); 1700238104Sdes} 1701238104Sdes 1702238104Sdesldns_status 1703238104Sdesldns_rr_list2buffer_str(ldns_buffer *output, const ldns_rr_list *list) 1704238104Sdes{ 1705238104Sdes return ldns_rr_list2buffer_str_fmt( 1706238104Sdes output, ldns_output_format_default, list); 1707238104Sdes} 1708238104Sdes 1709238104Sdesldns_status 1710238104Sdesldns_pktheader2buffer_str(ldns_buffer *output, const ldns_pkt *pkt) 1711238104Sdes{ 1712238104Sdes ldns_lookup_table *opcode = ldns_lookup_by_id(ldns_opcodes, 1713238104Sdes (int) ldns_pkt_get_opcode(pkt)); 1714238104Sdes ldns_lookup_table *rcode = ldns_lookup_by_id(ldns_rcodes, 1715238104Sdes (int) ldns_pkt_get_rcode(pkt)); 1716238104Sdes 1717238104Sdes ldns_buffer_printf(output, ";; ->>HEADER<<- "); 1718238104Sdes if (opcode) { 1719238104Sdes ldns_buffer_printf(output, "opcode: %s, ", opcode->name); 1720238104Sdes } else { 1721238104Sdes ldns_buffer_printf(output, "opcode: ?? (%u), ", 1722238104Sdes ldns_pkt_get_opcode(pkt)); 1723238104Sdes } 1724238104Sdes if (rcode) { 1725238104Sdes ldns_buffer_printf(output, "rcode: %s, ", rcode->name); 1726238104Sdes } else { 1727238104Sdes ldns_buffer_printf(output, "rcode: ?? (%u), ", ldns_pkt_get_rcode(pkt)); 1728238104Sdes } 1729238104Sdes ldns_buffer_printf(output, "id: %d\n", ldns_pkt_id(pkt)); 1730238104Sdes ldns_buffer_printf(output, ";; flags: "); 1731238104Sdes 1732238104Sdes if (ldns_pkt_qr(pkt)) { 1733238104Sdes ldns_buffer_printf(output, "qr "); 1734238104Sdes } 1735238104Sdes if (ldns_pkt_aa(pkt)) { 1736238104Sdes ldns_buffer_printf(output, "aa "); 1737238104Sdes } 1738238104Sdes if (ldns_pkt_tc(pkt)) { 1739238104Sdes ldns_buffer_printf(output, "tc "); 1740238104Sdes } 1741238104Sdes if (ldns_pkt_rd(pkt)) { 1742238104Sdes ldns_buffer_printf(output, "rd "); 1743238104Sdes } 1744238104Sdes if (ldns_pkt_cd(pkt)) { 1745238104Sdes ldns_buffer_printf(output, "cd "); 1746238104Sdes } 1747238104Sdes if (ldns_pkt_ra(pkt)) { 1748238104Sdes ldns_buffer_printf(output, "ra "); 1749238104Sdes } 1750238104Sdes if (ldns_pkt_ad(pkt)) { 1751238104Sdes ldns_buffer_printf(output, "ad "); 1752238104Sdes } 1753238104Sdes ldns_buffer_printf(output, "; "); 1754238104Sdes ldns_buffer_printf(output, "QUERY: %u, ", ldns_pkt_qdcount(pkt)); 1755238104Sdes ldns_buffer_printf(output, "ANSWER: %u, ", ldns_pkt_ancount(pkt)); 1756238104Sdes ldns_buffer_printf(output, "AUTHORITY: %u, ", ldns_pkt_nscount(pkt)); 1757238104Sdes ldns_buffer_printf(output, "ADDITIONAL: %u ", ldns_pkt_arcount(pkt)); 1758238104Sdes return ldns_buffer_status(output); 1759238104Sdes} 1760238104Sdes 1761238104Sdesldns_status 1762238104Sdesldns_pkt2buffer_str_fmt(ldns_buffer *output, 1763238104Sdes const ldns_output_format *fmt, const ldns_pkt *pkt) 1764238104Sdes{ 1765238104Sdes uint16_t i; 1766238104Sdes ldns_status status = LDNS_STATUS_OK; 1767238104Sdes char *tmp; 1768238104Sdes struct timeval time; 1769238104Sdes time_t time_tt; 1770238104Sdes 1771238104Sdes if (!pkt) { 1772238104Sdes ldns_buffer_printf(output, "null"); 1773238104Sdes return LDNS_STATUS_OK; 1774238104Sdes } 1775238104Sdes 1776238104Sdes if (ldns_buffer_status_ok(output)) { 1777238104Sdes status = ldns_pktheader2buffer_str(output, pkt); 1778238104Sdes if (status != LDNS_STATUS_OK) { 1779238104Sdes return status; 1780238104Sdes } 1781238104Sdes 1782238104Sdes ldns_buffer_printf(output, "\n"); 1783238104Sdes 1784238104Sdes ldns_buffer_printf(output, ";; QUESTION SECTION:\n;; "); 1785238104Sdes 1786238104Sdes 1787238104Sdes for (i = 0; i < ldns_pkt_qdcount(pkt); i++) { 1788238104Sdes status = ldns_rr2buffer_str_fmt(output, fmt, 1789238104Sdes ldns_rr_list_rr( 1790238104Sdes ldns_pkt_question(pkt), i)); 1791238104Sdes if (status != LDNS_STATUS_OK) { 1792238104Sdes return status; 1793238104Sdes } 1794238104Sdes } 1795238104Sdes ldns_buffer_printf(output, "\n"); 1796238104Sdes 1797238104Sdes ldns_buffer_printf(output, ";; ANSWER SECTION:\n"); 1798238104Sdes for (i = 0; i < ldns_pkt_ancount(pkt); i++) { 1799238104Sdes status = ldns_rr2buffer_str_fmt(output, fmt, 1800238104Sdes ldns_rr_list_rr( 1801238104Sdes ldns_pkt_answer(pkt), i)); 1802238104Sdes if (status != LDNS_STATUS_OK) { 1803238104Sdes return status; 1804238104Sdes } 1805238104Sdes 1806238104Sdes } 1807238104Sdes ldns_buffer_printf(output, "\n"); 1808238104Sdes 1809238104Sdes ldns_buffer_printf(output, ";; AUTHORITY SECTION:\n"); 1810238104Sdes 1811238104Sdes for (i = 0; i < ldns_pkt_nscount(pkt); i++) { 1812238104Sdes status = ldns_rr2buffer_str_fmt(output, fmt, 1813238104Sdes ldns_rr_list_rr( 1814238104Sdes ldns_pkt_authority(pkt), i)); 1815238104Sdes if (status != LDNS_STATUS_OK) { 1816238104Sdes return status; 1817238104Sdes } 1818238104Sdes } 1819238104Sdes ldns_buffer_printf(output, "\n"); 1820238104Sdes 1821238104Sdes ldns_buffer_printf(output, ";; ADDITIONAL SECTION:\n"); 1822238104Sdes for (i = 0; i < ldns_pkt_arcount(pkt); i++) { 1823238104Sdes status = ldns_rr2buffer_str_fmt(output, fmt, 1824238104Sdes ldns_rr_list_rr( 1825238104Sdes ldns_pkt_additional(pkt), i)); 1826238104Sdes if (status != LDNS_STATUS_OK) { 1827238104Sdes return status; 1828238104Sdes } 1829238104Sdes 1830238104Sdes } 1831238104Sdes ldns_buffer_printf(output, "\n"); 1832238104Sdes /* add some futher fields */ 1833238104Sdes ldns_buffer_printf(output, ";; Query time: %d msec\n", 1834238104Sdes ldns_pkt_querytime(pkt)); 1835238104Sdes if (ldns_pkt_edns(pkt)) { 1836238104Sdes ldns_buffer_printf(output, 1837238104Sdes ";; EDNS: version %u; flags:", 1838238104Sdes ldns_pkt_edns_version(pkt)); 1839238104Sdes if (ldns_pkt_edns_do(pkt)) { 1840238104Sdes ldns_buffer_printf(output, " do"); 1841238104Sdes } 1842238104Sdes /* the extended rcode is the value set, shifted four bits, 1843238104Sdes * and or'd with the original rcode */ 1844238104Sdes if (ldns_pkt_edns_extended_rcode(pkt)) { 1845238104Sdes ldns_buffer_printf(output, " ; ext-rcode: %d", 1846238104Sdes (ldns_pkt_edns_extended_rcode(pkt) << 4 | ldns_pkt_get_rcode(pkt))); 1847238104Sdes } 1848238104Sdes ldns_buffer_printf(output, " ; udp: %u\n", 1849238104Sdes ldns_pkt_edns_udp_size(pkt)); 1850238104Sdes 1851238104Sdes if (ldns_pkt_edns_data(pkt)) { 1852238104Sdes ldns_buffer_printf(output, ";; Data: "); 1853238104Sdes (void)ldns_rdf2buffer_str(output, 1854238104Sdes ldns_pkt_edns_data(pkt)); 1855238104Sdes ldns_buffer_printf(output, "\n"); 1856238104Sdes } 1857238104Sdes } 1858238104Sdes if (ldns_pkt_tsig(pkt)) { 1859238104Sdes ldns_buffer_printf(output, ";; TSIG:\n;; "); 1860238104Sdes (void) ldns_rr2buffer_str_fmt( 1861238104Sdes output, fmt, ldns_pkt_tsig(pkt)); 1862238104Sdes ldns_buffer_printf(output, "\n"); 1863238104Sdes } 1864238104Sdes if (ldns_pkt_answerfrom(pkt)) { 1865238104Sdes tmp = ldns_rdf2str(ldns_pkt_answerfrom(pkt)); 1866238104Sdes ldns_buffer_printf(output, ";; SERVER: %s\n", tmp); 1867238104Sdes LDNS_FREE(tmp); 1868238104Sdes } 1869238104Sdes time = ldns_pkt_timestamp(pkt); 1870238104Sdes time_tt = (time_t)time.tv_sec; 1871238104Sdes ldns_buffer_printf(output, ";; WHEN: %s", 1872238104Sdes (char*)ctime(&time_tt)); 1873238104Sdes 1874238104Sdes ldns_buffer_printf(output, ";; MSG SIZE rcvd: %d\n", 1875238104Sdes (int)ldns_pkt_size(pkt)); 1876238104Sdes } else { 1877238104Sdes return ldns_buffer_status(output); 1878238104Sdes } 1879238104Sdes return status; 1880238104Sdes} 1881238104Sdes 1882238104Sdesldns_status 1883238104Sdesldns_pkt2buffer_str(ldns_buffer *output, const ldns_pkt *pkt) 1884238104Sdes{ 1885238104Sdes return ldns_pkt2buffer_str_fmt(output, ldns_output_format_default, pkt); 1886238104Sdes} 1887238104Sdes 1888238104Sdes 1889238104Sdes#ifdef HAVE_SSL 1890238104Sdesstatic ldns_status 1891238104Sdesldns_hmac_key2buffer_str(ldns_buffer *output, const ldns_key *k) 1892238104Sdes{ 1893238104Sdes ldns_status status; 1894238104Sdes size_t i; 1895238104Sdes ldns_rdf *b64_bignum; 1896238104Sdes 1897238104Sdes ldns_buffer_printf(output, "Key: "); 1898238104Sdes 1899238104Sdes i = ldns_key_hmac_size(k); 1900238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, ldns_key_hmac_key(k)); 1901238104Sdes status = ldns_rdf2buffer_str(output, b64_bignum); 1902238104Sdes ldns_rdf_deep_free(b64_bignum); 1903238104Sdes ldns_buffer_printf(output, "\n"); 1904238104Sdes return status; 1905238104Sdes} 1906238104Sdes#endif 1907238104Sdes 1908238104Sdes#if defined(HAVE_SSL) && defined(USE_GOST) 1909238104Sdesstatic ldns_status 1910238104Sdesldns_gost_key2buffer_str(ldns_buffer *output, EVP_PKEY *p) 1911238104Sdes{ 1912238104Sdes unsigned char* pp = NULL; 1913238104Sdes int ret; 1914238104Sdes ldns_rdf *b64_bignum; 1915238104Sdes ldns_status status; 1916238104Sdes 1917238104Sdes ldns_buffer_printf(output, "GostAsn1: "); 1918238104Sdes 1919238104Sdes ret = i2d_PrivateKey(p, &pp); 1920238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, (size_t)ret, pp); 1921238104Sdes status = ldns_rdf2buffer_str(output, b64_bignum); 1922238104Sdes 1923238104Sdes ldns_rdf_deep_free(b64_bignum); 1924238104Sdes OPENSSL_free(pp); 1925238104Sdes ldns_buffer_printf(output, "\n"); 1926238104Sdes return status; 1927238104Sdes} 1928238104Sdes#endif 1929238104Sdes 1930238104Sdesldns_status 1931238104Sdesldns_key2buffer_str(ldns_buffer *output, const ldns_key *k) 1932238104Sdes{ 1933238104Sdes ldns_status status = LDNS_STATUS_OK; 1934238104Sdes unsigned char *bignum; 1935246854Sdes#ifdef HAVE_SSL 1936246854Sdes# ifndef S_SPLINT_S 1937238104Sdes uint16_t i; 1938246854Sdes# endif 1939238104Sdes /* not used when ssl is not defined */ 1940246854Sdes /*@unused@*/ 1941238104Sdes ldns_rdf *b64_bignum = NULL; 1942238104Sdes 1943238104Sdes RSA *rsa; 1944238104Sdes DSA *dsa; 1945238104Sdes#endif /* HAVE_SSL */ 1946238104Sdes 1947238104Sdes if (!k) { 1948238104Sdes return LDNS_STATUS_ERR; 1949238104Sdes } 1950238104Sdes 1951238104Sdes bignum = LDNS_XMALLOC(unsigned char, LDNS_MAX_KEYLEN); 1952238104Sdes if (!bignum) { 1953238104Sdes return LDNS_STATUS_ERR; 1954238104Sdes } 1955238104Sdes 1956238104Sdes if (ldns_buffer_status_ok(output)) { 1957238104Sdes#ifdef HAVE_SSL 1958238104Sdes switch(ldns_key_algorithm(k)) { 1959238104Sdes case LDNS_SIGN_RSASHA1: 1960238104Sdes case LDNS_SIGN_RSASHA1_NSEC3: 1961238104Sdes case LDNS_SIGN_RSASHA256: 1962238104Sdes case LDNS_SIGN_RSASHA512: 1963238104Sdes case LDNS_SIGN_RSAMD5: 1964238104Sdes /* copied by looking at dnssec-keygen output */ 1965238104Sdes /* header */ 1966238104Sdes rsa = ldns_key_rsa_key(k); 1967238104Sdes 1968238104Sdes ldns_buffer_printf(output,"Private-key-format: v1.2\n"); 1969238104Sdes switch(ldns_key_algorithm(k)) { 1970238104Sdes case LDNS_SIGN_RSAMD5: 1971238104Sdes ldns_buffer_printf(output, 1972238104Sdes "Algorithm: %u (RSA)\n", 1973238104Sdes LDNS_RSAMD5); 1974238104Sdes break; 1975238104Sdes case LDNS_SIGN_RSASHA1: 1976238104Sdes ldns_buffer_printf(output, 1977238104Sdes "Algorithm: %u (RSASHA1)\n", 1978238104Sdes LDNS_RSASHA1); 1979238104Sdes break; 1980238104Sdes case LDNS_SIGN_RSASHA1_NSEC3: 1981238104Sdes ldns_buffer_printf(output, 1982238104Sdes "Algorithm: %u (RSASHA1_NSEC3)\n", 1983238104Sdes LDNS_RSASHA1_NSEC3); 1984238104Sdes break; 1985238104Sdes#ifdef USE_SHA2 1986238104Sdes case LDNS_SIGN_RSASHA256: 1987238104Sdes ldns_buffer_printf(output, 1988238104Sdes "Algorithm: %u (RSASHA256)\n", 1989238104Sdes LDNS_RSASHA256); 1990238104Sdes break; 1991238104Sdes case LDNS_SIGN_RSASHA512: 1992238104Sdes ldns_buffer_printf(output, 1993238104Sdes "Algorithm: %u (RSASHA512)\n", 1994238104Sdes LDNS_RSASHA512); 1995238104Sdes break; 1996238104Sdes#endif 1997238104Sdes default: 1998266114Sdes#ifdef STDERR_MSGS 1999238104Sdes fprintf(stderr, "Warning: unknown signature "); 2000238104Sdes fprintf(stderr, 2001238104Sdes "algorithm type %u\n", 2002238104Sdes ldns_key_algorithm(k)); 2003266114Sdes#endif 2004238104Sdes ldns_buffer_printf(output, 2005238104Sdes "Algorithm: %u (Unknown)\n", 2006238104Sdes ldns_key_algorithm(k)); 2007238104Sdes break; 2008238104Sdes } 2009238104Sdes 2010238104Sdes /* print to buf, convert to bin, convert to b64, 2011238104Sdes * print to buf */ 2012238104Sdes ldns_buffer_printf(output, "Modulus: "); 2013238104Sdes#ifndef S_SPLINT_S 2014238104Sdes i = (uint16_t)BN_bn2bin(rsa->n, bignum); 2015238104Sdes if (i > LDNS_MAX_KEYLEN) { 2016238104Sdes goto error; 2017238104Sdes } 2018238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2019238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2020246854Sdes ldns_rdf_deep_free(b64_bignum); 2021238104Sdes goto error; 2022238104Sdes } 2023238104Sdes ldns_rdf_deep_free(b64_bignum); 2024238104Sdes ldns_buffer_printf(output, "\n"); 2025238104Sdes ldns_buffer_printf(output, "PublicExponent: "); 2026238104Sdes i = (uint16_t)BN_bn2bin(rsa->e, bignum); 2027238104Sdes if (i > LDNS_MAX_KEYLEN) { 2028238104Sdes goto error; 2029238104Sdes } 2030238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2031238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2032246854Sdes ldns_rdf_deep_free(b64_bignum); 2033238104Sdes goto error; 2034238104Sdes } 2035238104Sdes ldns_rdf_deep_free(b64_bignum); 2036238104Sdes ldns_buffer_printf(output, "\n"); 2037238104Sdes 2038238104Sdes ldns_buffer_printf(output, "PrivateExponent: "); 2039238104Sdes if (rsa->d) { 2040238104Sdes i = (uint16_t)BN_bn2bin(rsa->d, bignum); 2041238104Sdes if (i > LDNS_MAX_KEYLEN) { 2042238104Sdes goto error; 2043238104Sdes } 2044238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2045238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2046246854Sdes ldns_rdf_deep_free(b64_bignum); 2047238104Sdes goto error; 2048238104Sdes } 2049238104Sdes ldns_rdf_deep_free(b64_bignum); 2050238104Sdes ldns_buffer_printf(output, "\n"); 2051238104Sdes } else { 2052238104Sdes ldns_buffer_printf(output, "(Not available)\n"); 2053238104Sdes } 2054238104Sdes 2055238104Sdes ldns_buffer_printf(output, "Prime1: "); 2056238104Sdes if (rsa->p) { 2057238104Sdes i = (uint16_t)BN_bn2bin(rsa->p, bignum); 2058238104Sdes if (i > LDNS_MAX_KEYLEN) { 2059238104Sdes goto error; 2060238104Sdes } 2061238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2062238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2063246854Sdes ldns_rdf_deep_free(b64_bignum); 2064238104Sdes goto error; 2065238104Sdes } 2066238104Sdes ldns_rdf_deep_free(b64_bignum); 2067238104Sdes ldns_buffer_printf(output, "\n"); 2068238104Sdes } else { 2069238104Sdes ldns_buffer_printf(output, "(Not available)\n"); 2070238104Sdes } 2071238104Sdes 2072238104Sdes ldns_buffer_printf(output, "Prime2: "); 2073238104Sdes if (rsa->q) { 2074238104Sdes i = (uint16_t)BN_bn2bin(rsa->q, bignum); 2075238104Sdes if (i > LDNS_MAX_KEYLEN) { 2076238104Sdes goto error; 2077238104Sdes } 2078238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2079238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2080246854Sdes ldns_rdf_deep_free(b64_bignum); 2081238104Sdes goto error; 2082238104Sdes } 2083238104Sdes ldns_rdf_deep_free(b64_bignum); 2084238104Sdes ldns_buffer_printf(output, "\n"); 2085238104Sdes } else { 2086238104Sdes ldns_buffer_printf(output, "(Not available)\n"); 2087238104Sdes } 2088238104Sdes 2089238104Sdes ldns_buffer_printf(output, "Exponent1: "); 2090238104Sdes if (rsa->dmp1) { 2091238104Sdes i = (uint16_t)BN_bn2bin(rsa->dmp1, bignum); 2092238104Sdes if (i > LDNS_MAX_KEYLEN) { 2093238104Sdes goto error; 2094238104Sdes } 2095238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2096238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2097246854Sdes ldns_rdf_deep_free(b64_bignum); 2098238104Sdes goto error; 2099238104Sdes } 2100238104Sdes ldns_rdf_deep_free(b64_bignum); 2101238104Sdes ldns_buffer_printf(output, "\n"); 2102238104Sdes } else { 2103238104Sdes ldns_buffer_printf(output, "(Not available)\n"); 2104238104Sdes } 2105238104Sdes 2106238104Sdes ldns_buffer_printf(output, "Exponent2: "); 2107238104Sdes if (rsa->dmq1) { 2108238104Sdes i = (uint16_t)BN_bn2bin(rsa->dmq1, bignum); 2109238104Sdes if (i > LDNS_MAX_KEYLEN) { 2110238104Sdes goto error; 2111238104Sdes } 2112238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2113238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2114246854Sdes ldns_rdf_deep_free(b64_bignum); 2115238104Sdes goto error; 2116238104Sdes } 2117238104Sdes ldns_rdf_deep_free(b64_bignum); 2118238104Sdes ldns_buffer_printf(output, "\n"); 2119238104Sdes } else { 2120238104Sdes ldns_buffer_printf(output, "(Not available)\n"); 2121238104Sdes } 2122238104Sdes 2123238104Sdes ldns_buffer_printf(output, "Coefficient: "); 2124238104Sdes if (rsa->iqmp) { 2125238104Sdes i = (uint16_t)BN_bn2bin(rsa->iqmp, bignum); 2126238104Sdes if (i > LDNS_MAX_KEYLEN) { 2127238104Sdes goto error; 2128238104Sdes } 2129238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2130238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2131246854Sdes ldns_rdf_deep_free(b64_bignum); 2132238104Sdes goto error; 2133238104Sdes } 2134238104Sdes ldns_rdf_deep_free(b64_bignum); 2135238104Sdes ldns_buffer_printf(output, "\n"); 2136238104Sdes } else { 2137238104Sdes ldns_buffer_printf(output, "(Not available)\n"); 2138238104Sdes } 2139238104Sdes#endif /* splint */ 2140238104Sdes 2141238104Sdes RSA_free(rsa); 2142238104Sdes break; 2143238104Sdes case LDNS_SIGN_DSA: 2144238104Sdes case LDNS_SIGN_DSA_NSEC3: 2145238104Sdes dsa = ldns_key_dsa_key(k); 2146238104Sdes 2147238104Sdes ldns_buffer_printf(output,"Private-key-format: v1.2\n"); 2148238104Sdes if (ldns_key_algorithm(k) == LDNS_SIGN_DSA) { 2149238104Sdes ldns_buffer_printf(output,"Algorithm: 3 (DSA)\n"); 2150238104Sdes } else if (ldns_key_algorithm(k) == LDNS_SIGN_DSA_NSEC3) { 2151238104Sdes ldns_buffer_printf(output,"Algorithm: 6 (DSA_NSEC3)\n"); 2152238104Sdes } 2153238104Sdes 2154238104Sdes /* print to buf, convert to bin, convert to b64, 2155238104Sdes * print to buf */ 2156238104Sdes ldns_buffer_printf(output, "Prime(p): "); 2157238104Sdes#ifndef S_SPLINT_S 2158238104Sdes if (dsa->p) { 2159238104Sdes i = (uint16_t)BN_bn2bin(dsa->p, bignum); 2160238104Sdes if (i > LDNS_MAX_KEYLEN) { 2161238104Sdes goto error; 2162238104Sdes } 2163238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2164238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2165246854Sdes ldns_rdf_deep_free(b64_bignum); 2166238104Sdes goto error; 2167238104Sdes } 2168238104Sdes ldns_rdf_deep_free(b64_bignum); 2169238104Sdes ldns_buffer_printf(output, "\n"); 2170238104Sdes } else { 2171238104Sdes printf("(Not available)\n"); 2172238104Sdes } 2173238104Sdes 2174238104Sdes ldns_buffer_printf(output, "Subprime(q): "); 2175238104Sdes if (dsa->q) { 2176238104Sdes i = (uint16_t)BN_bn2bin(dsa->q, bignum); 2177238104Sdes if (i > LDNS_MAX_KEYLEN) { 2178238104Sdes goto error; 2179238104Sdes } 2180238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2181238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2182246854Sdes ldns_rdf_deep_free(b64_bignum); 2183238104Sdes goto error; 2184238104Sdes } 2185238104Sdes ldns_rdf_deep_free(b64_bignum); 2186238104Sdes ldns_buffer_printf(output, "\n"); 2187238104Sdes } else { 2188238104Sdes printf("(Not available)\n"); 2189238104Sdes } 2190238104Sdes 2191238104Sdes ldns_buffer_printf(output, "Base(g): "); 2192238104Sdes if (dsa->g) { 2193238104Sdes i = (uint16_t)BN_bn2bin(dsa->g, bignum); 2194238104Sdes if (i > LDNS_MAX_KEYLEN) { 2195238104Sdes goto error; 2196238104Sdes } 2197238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2198238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2199246854Sdes ldns_rdf_deep_free(b64_bignum); 2200238104Sdes goto error; 2201238104Sdes } 2202238104Sdes ldns_rdf_deep_free(b64_bignum); 2203238104Sdes ldns_buffer_printf(output, "\n"); 2204238104Sdes } else { 2205238104Sdes printf("(Not available)\n"); 2206238104Sdes } 2207238104Sdes 2208238104Sdes ldns_buffer_printf(output, "Private_value(x): "); 2209238104Sdes if (dsa->priv_key) { 2210238104Sdes i = (uint16_t)BN_bn2bin(dsa->priv_key, bignum); 2211238104Sdes if (i > LDNS_MAX_KEYLEN) { 2212238104Sdes goto error; 2213238104Sdes } 2214238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2215238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2216246854Sdes ldns_rdf_deep_free(b64_bignum); 2217238104Sdes goto error; 2218238104Sdes } 2219238104Sdes ldns_rdf_deep_free(b64_bignum); 2220238104Sdes ldns_buffer_printf(output, "\n"); 2221238104Sdes } else { 2222238104Sdes printf("(Not available)\n"); 2223238104Sdes } 2224238104Sdes 2225238104Sdes ldns_buffer_printf(output, "Public_value(y): "); 2226238104Sdes if (dsa->pub_key) { 2227238104Sdes i = (uint16_t)BN_bn2bin(dsa->pub_key, bignum); 2228238104Sdes if (i > LDNS_MAX_KEYLEN) { 2229238104Sdes goto error; 2230238104Sdes } 2231238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2232238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2233246854Sdes ldns_rdf_deep_free(b64_bignum); 2234238104Sdes goto error; 2235238104Sdes } 2236238104Sdes ldns_rdf_deep_free(b64_bignum); 2237238104Sdes ldns_buffer_printf(output, "\n"); 2238238104Sdes } else { 2239238104Sdes printf("(Not available)\n"); 2240238104Sdes } 2241238104Sdes#endif /* splint */ 2242238104Sdes break; 2243238104Sdes case LDNS_SIGN_ECC_GOST: 2244238104Sdes /* no format defined, use blob */ 2245238104Sdes#if defined(HAVE_SSL) && defined(USE_GOST) 2246238104Sdes ldns_buffer_printf(output, "Private-key-format: v1.2\n"); 2247238104Sdes ldns_buffer_printf(output, "Algorithm: %d (ECC-GOST)\n", LDNS_SIGN_ECC_GOST); 2248238104Sdes status = ldns_gost_key2buffer_str(output, 2249238104Sdes#ifndef S_SPLINT_S 2250238104Sdes k->_key.key 2251238104Sdes#else 2252238104Sdes NULL 2253238104Sdes#endif 2254238104Sdes ); 2255238104Sdes#else 2256238104Sdes goto error; 2257238104Sdes#endif /* GOST */ 2258238104Sdes break; 2259238104Sdes case LDNS_SIGN_ECDSAP256SHA256: 2260238104Sdes case LDNS_SIGN_ECDSAP384SHA384: 2261238104Sdes#ifdef USE_ECDSA 2262238104Sdes ldns_buffer_printf(output, "Private-key-format: v1.2\n"); 2263238104Sdes ldns_buffer_printf(output, "Algorithm: %d (", ldns_key_algorithm(k)); 2264238104Sdes status=ldns_algorithm2buffer_str(output, (ldns_algorithm)ldns_key_algorithm(k)); 2265238104Sdes#ifndef S_SPLINT_S 2266238104Sdes ldns_buffer_printf(output, ")\n"); 2267238104Sdes if(k->_key.key) { 2268238104Sdes EC_KEY* ec = EVP_PKEY_get1_EC_KEY(k->_key.key); 2269238104Sdes const BIGNUM* b = EC_KEY_get0_private_key(ec); 2270238104Sdes ldns_buffer_printf(output, "PrivateKey: "); 2271238104Sdes i = (uint16_t)BN_bn2bin(b, bignum); 2272238104Sdes if (i > LDNS_MAX_KEYLEN) { 2273238104Sdes goto error; 2274238104Sdes } 2275238104Sdes b64_bignum = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_B64, i, bignum); 2276238104Sdes if (ldns_rdf2buffer_str(output, b64_bignum) != LDNS_STATUS_OK) { 2277246854Sdes ldns_rdf_deep_free(b64_bignum); 2278238104Sdes goto error; 2279238104Sdes } 2280238104Sdes ldns_rdf_deep_free(b64_bignum); 2281238104Sdes ldns_buffer_printf(output, "\n"); 2282238104Sdes /* down reference count in EC_KEY 2283238104Sdes * its still assigned to the PKEY */ 2284238104Sdes EC_KEY_free(ec); 2285238104Sdes } 2286238104Sdes#endif /* splint */ 2287238104Sdes#else 2288238104Sdes goto error; 2289238104Sdes#endif /* ECDSA */ 2290238104Sdes break; 2291238104Sdes case LDNS_SIGN_HMACMD5: 2292238104Sdes /* there's not much of a format defined for TSIG */ 2293238104Sdes /* It's just a binary blob, Same for all algorithms */ 2294238104Sdes ldns_buffer_printf(output, "Private-key-format: v1.2\n"); 2295238104Sdes ldns_buffer_printf(output, "Algorithm: 157 (HMAC_MD5)\n"); 2296238104Sdes status = ldns_hmac_key2buffer_str(output, k); 2297238104Sdes break; 2298238104Sdes case LDNS_SIGN_HMACSHA1: 2299238104Sdes ldns_buffer_printf(output, "Private-key-format: v1.2\n"); 2300238104Sdes ldns_buffer_printf(output, "Algorithm: 158 (HMAC_SHA1)\n"); 2301238104Sdes status = ldns_hmac_key2buffer_str(output, k); 2302238104Sdes break; 2303238104Sdes case LDNS_SIGN_HMACSHA256: 2304238104Sdes ldns_buffer_printf(output, "Private-key-format: v1.2\n"); 2305238104Sdes ldns_buffer_printf(output, "Algorithm: 159 (HMAC_SHA256)\n"); 2306238104Sdes status = ldns_hmac_key2buffer_str(output, k); 2307238104Sdes break; 2308238104Sdes } 2309238104Sdes#endif /* HAVE_SSL */ 2310238104Sdes } else { 2311238104Sdes LDNS_FREE(bignum); 2312238104Sdes return ldns_buffer_status(output); 2313238104Sdes } 2314238104Sdes LDNS_FREE(bignum); 2315238104Sdes return status; 2316238104Sdes 2317238104Sdes#ifdef HAVE_SSL 2318238104Sdes /* compiles warn the label isn't used */ 2319238104Sdeserror: 2320238104Sdes LDNS_FREE(bignum); 2321238104Sdes return LDNS_STATUS_ERR; 2322238104Sdes#endif /* HAVE_SSL */ 2323238104Sdes 2324238104Sdes} 2325238104Sdes 2326238104Sdes/* 2327246854Sdes * Zero terminate the buffer and copy data. 2328238104Sdes */ 2329238104Sdeschar * 2330238104Sdesldns_buffer2str(ldns_buffer *buffer) 2331238104Sdes{ 2332238104Sdes char *str; 2333238104Sdes 2334238104Sdes /* check if buffer ends with \0, if not, and 2335238104Sdes if there is space, add it */ 2336238104Sdes if (*(ldns_buffer_at(buffer, ldns_buffer_position(buffer))) != 0) { 2337238104Sdes if (!ldns_buffer_reserve(buffer, 1)) { 2338238104Sdes return NULL; 2339238104Sdes } 2340238104Sdes ldns_buffer_write_u8(buffer, (uint8_t) '\0'); 2341238104Sdes if (!ldns_buffer_set_capacity(buffer, ldns_buffer_position(buffer))) { 2342238104Sdes return NULL; 2343238104Sdes } 2344238104Sdes } 2345238104Sdes 2346246854Sdes str = strdup((const char *)ldns_buffer_begin(buffer)); 2347238104Sdes if(!str) { 2348238104Sdes return NULL; 2349238104Sdes } 2350238104Sdes return str; 2351238104Sdes} 2352238104Sdes 2353246854Sdes/* 2354246854Sdes * Zero terminate the buffer and export data. 2355246854Sdes */ 2356238104Sdeschar * 2357246854Sdesldns_buffer_export2str(ldns_buffer *buffer) 2358246854Sdes{ 2359246854Sdes /* Append '\0' as string terminator */ 2360246854Sdes if (! ldns_buffer_reserve(buffer, 1)) { 2361246854Sdes return NULL; 2362246854Sdes } 2363246854Sdes ldns_buffer_write_u8(buffer, 0); 2364246854Sdes 2365246854Sdes /* reallocate memory to the size of the string and export */ 2366246854Sdes ldns_buffer_set_capacity(buffer, ldns_buffer_position(buffer)); 2367246854Sdes return ldns_buffer_export(buffer); 2368246854Sdes} 2369246854Sdes 2370246854Sdeschar * 2371238104Sdesldns_rdf2str(const ldns_rdf *rdf) 2372238104Sdes{ 2373238104Sdes char *result = NULL; 2374238104Sdes ldns_buffer *tmp_buffer = ldns_buffer_new(LDNS_MAX_PACKETLEN); 2375238104Sdes 2376238104Sdes if (!tmp_buffer) { 2377238104Sdes return NULL; 2378238104Sdes } 2379238104Sdes if (ldns_rdf2buffer_str(tmp_buffer, rdf) == LDNS_STATUS_OK) { 2380238104Sdes /* export and return string, destroy rest */ 2381246854Sdes result = ldns_buffer_export2str(tmp_buffer); 2382238104Sdes } 2383238104Sdes ldns_buffer_free(tmp_buffer); 2384238104Sdes return result; 2385238104Sdes} 2386238104Sdes 2387238104Sdeschar * 2388238104Sdesldns_rr2str_fmt(const ldns_output_format *fmt, const ldns_rr *rr) 2389238104Sdes{ 2390238104Sdes char *result = NULL; 2391238104Sdes ldns_buffer *tmp_buffer = ldns_buffer_new(LDNS_MAX_PACKETLEN); 2392238104Sdes 2393238104Sdes if (!tmp_buffer) { 2394238104Sdes return NULL; 2395238104Sdes } 2396238104Sdes if (ldns_rr2buffer_str_fmt(tmp_buffer, fmt, rr) 2397238104Sdes == LDNS_STATUS_OK) { 2398238104Sdes /* export and return string, destroy rest */ 2399246854Sdes result = ldns_buffer_export2str(tmp_buffer); 2400238104Sdes } 2401238104Sdes ldns_buffer_free(tmp_buffer); 2402238104Sdes return result; 2403238104Sdes} 2404238104Sdes 2405238104Sdeschar * 2406238104Sdesldns_rr2str(const ldns_rr *rr) 2407238104Sdes{ 2408238104Sdes return ldns_rr2str_fmt(ldns_output_format_default, rr); 2409238104Sdes} 2410238104Sdes 2411238104Sdeschar * 2412238104Sdesldns_pkt2str_fmt(const ldns_output_format *fmt, const ldns_pkt *pkt) 2413238104Sdes{ 2414238104Sdes char *result = NULL; 2415238104Sdes ldns_buffer *tmp_buffer = ldns_buffer_new(LDNS_MAX_PACKETLEN); 2416238104Sdes 2417238104Sdes if (!tmp_buffer) { 2418238104Sdes return NULL; 2419238104Sdes } 2420238104Sdes if (ldns_pkt2buffer_str_fmt(tmp_buffer, fmt, pkt) 2421238104Sdes == LDNS_STATUS_OK) { 2422238104Sdes /* export and return string, destroy rest */ 2423246854Sdes result = ldns_buffer_export2str(tmp_buffer); 2424238104Sdes } 2425238104Sdes 2426238104Sdes ldns_buffer_free(tmp_buffer); 2427238104Sdes return result; 2428238104Sdes} 2429238104Sdes 2430238104Sdeschar * 2431238104Sdesldns_pkt2str(const ldns_pkt *pkt) 2432238104Sdes{ 2433238104Sdes return ldns_pkt2str_fmt(ldns_output_format_default, pkt); 2434238104Sdes} 2435238104Sdes 2436238104Sdeschar * 2437238104Sdesldns_key2str(const ldns_key *k) 2438238104Sdes{ 2439238104Sdes char *result = NULL; 2440238104Sdes ldns_buffer *tmp_buffer = ldns_buffer_new(LDNS_MAX_PACKETLEN); 2441238104Sdes 2442238104Sdes if (!tmp_buffer) { 2443238104Sdes return NULL; 2444238104Sdes } 2445238104Sdes if (ldns_key2buffer_str(tmp_buffer, k) == LDNS_STATUS_OK) { 2446238104Sdes /* export and return string, destroy rest */ 2447246854Sdes result = ldns_buffer_export2str(tmp_buffer); 2448238104Sdes } 2449238104Sdes ldns_buffer_free(tmp_buffer); 2450238104Sdes return result; 2451238104Sdes} 2452238104Sdes 2453238104Sdeschar * 2454238104Sdesldns_rr_list2str_fmt(const ldns_output_format *fmt, const ldns_rr_list *list) 2455238104Sdes{ 2456238104Sdes char *result = NULL; 2457238104Sdes ldns_buffer *tmp_buffer = ldns_buffer_new(LDNS_MAX_PACKETLEN); 2458238104Sdes 2459238104Sdes if (!tmp_buffer) { 2460238104Sdes return NULL; 2461238104Sdes } 2462238104Sdes if (list) { 2463238104Sdes if (ldns_rr_list2buffer_str_fmt( 2464238104Sdes tmp_buffer, fmt, list) 2465238104Sdes == LDNS_STATUS_OK) { 2466238104Sdes } 2467238104Sdes } else { 2468238104Sdes if (fmt == NULL) { 2469238104Sdes fmt = ldns_output_format_default; 2470238104Sdes } 2471238104Sdes if (fmt->flags & LDNS_COMMENT_NULLS) { 2472238104Sdes ldns_buffer_printf(tmp_buffer, "; (null)\n"); 2473238104Sdes } 2474238104Sdes } 2475238104Sdes 2476238104Sdes /* export and return string, destroy rest */ 2477246854Sdes result = ldns_buffer_export2str(tmp_buffer); 2478238104Sdes ldns_buffer_free(tmp_buffer); 2479238104Sdes return result; 2480238104Sdes} 2481238104Sdes 2482238104Sdeschar * 2483238104Sdesldns_rr_list2str(const ldns_rr_list *list) 2484238104Sdes{ 2485238104Sdes return ldns_rr_list2str_fmt(ldns_output_format_default, list); 2486238104Sdes} 2487238104Sdes 2488238104Sdesvoid 2489238104Sdesldns_rdf_print(FILE *output, const ldns_rdf *rdf) 2490238104Sdes{ 2491238104Sdes char *str = ldns_rdf2str(rdf); 2492238104Sdes if (str) { 2493238104Sdes fprintf(output, "%s", str); 2494238104Sdes } else { 2495246854Sdes fprintf(output, ";Unable to convert rdf to string\n"); 2496238104Sdes } 2497238104Sdes LDNS_FREE(str); 2498238104Sdes} 2499238104Sdes 2500238104Sdesvoid 2501246854Sdesldns_rr_print_fmt(FILE *output, 2502238104Sdes const ldns_output_format *fmt, const ldns_rr *rr) 2503238104Sdes{ 2504238104Sdes char *str = ldns_rr2str_fmt(fmt, rr); 2505238104Sdes if (str) { 2506238104Sdes fprintf(output, "%s", str); 2507238104Sdes } else { 2508246854Sdes fprintf(output, ";Unable to convert rr to string\n"); 2509238104Sdes } 2510238104Sdes LDNS_FREE(str); 2511238104Sdes} 2512238104Sdes 2513238104Sdesvoid 2514238104Sdesldns_rr_print(FILE *output, const ldns_rr *rr) 2515238104Sdes{ 2516238104Sdes ldns_rr_print_fmt(output, ldns_output_format_default, rr); 2517238104Sdes} 2518238104Sdes 2519238104Sdesvoid 2520238104Sdesldns_pkt_print_fmt(FILE *output, 2521238104Sdes const ldns_output_format *fmt, const ldns_pkt *pkt) 2522238104Sdes{ 2523238104Sdes char *str = ldns_pkt2str_fmt(fmt, pkt); 2524238104Sdes if (str) { 2525238104Sdes fprintf(output, "%s", str); 2526238104Sdes } else { 2527246854Sdes fprintf(output, ";Unable to convert packet to string\n"); 2528238104Sdes } 2529238104Sdes LDNS_FREE(str); 2530238104Sdes} 2531238104Sdes 2532238104Sdesvoid 2533238104Sdesldns_pkt_print(FILE *output, const ldns_pkt *pkt) 2534238104Sdes{ 2535238104Sdes ldns_pkt_print_fmt(output, ldns_output_format_default, pkt); 2536238104Sdes} 2537238104Sdes 2538238104Sdesvoid 2539238104Sdesldns_rr_list_print_fmt(FILE *output, 2540238104Sdes const ldns_output_format *fmt, const ldns_rr_list *lst) 2541238104Sdes{ 2542238104Sdes size_t i; 2543238104Sdes for (i = 0; i < ldns_rr_list_rr_count(lst); i++) { 2544238104Sdes ldns_rr_print_fmt(output, fmt, ldns_rr_list_rr(lst, i)); 2545238104Sdes } 2546238104Sdes} 2547238104Sdes 2548238104Sdesvoid 2549238104Sdesldns_rr_list_print(FILE *output, const ldns_rr_list *lst) 2550238104Sdes{ 2551238104Sdes ldns_rr_list_print_fmt(output, ldns_output_format_default, lst); 2552238104Sdes} 2553238104Sdes 2554238104Sdesvoid 2555238104Sdesldns_resolver_print_fmt(FILE *output, 2556238104Sdes const ldns_output_format *fmt, const ldns_resolver *r) 2557238104Sdes{ 2558238104Sdes uint16_t i; 2559238104Sdes ldns_rdf **n; 2560238104Sdes ldns_rdf **s; 2561238104Sdes size_t *rtt; 2562238104Sdes if (!r) { 2563238104Sdes return; 2564238104Sdes } 2565238104Sdes n = ldns_resolver_nameservers(r); 2566238104Sdes s = ldns_resolver_searchlist(r); 2567238104Sdes rtt = ldns_resolver_rtt(r); 2568238104Sdes 2569238104Sdes fprintf(output, "port: %d\n", (int)ldns_resolver_port(r)); 2570238104Sdes fprintf(output, "edns0 size: %d\n", (int)ldns_resolver_edns_udp_size(r)); 2571238104Sdes fprintf(output, "use ip6: %d\n", (int)ldns_resolver_ip6(r)); 2572238104Sdes 2573238104Sdes fprintf(output, "recursive: %d\n", ldns_resolver_recursive(r)); 2574238104Sdes fprintf(output, "usevc: %d\n", ldns_resolver_usevc(r)); 2575238104Sdes fprintf(output, "igntc: %d\n", ldns_resolver_igntc(r)); 2576238104Sdes fprintf(output, "fail: %d\n", ldns_resolver_fail(r)); 2577238104Sdes fprintf(output, "retry: %d\n", (int)ldns_resolver_retry(r)); 2578238104Sdes fprintf(output, "retrans: %d\n", (int)ldns_resolver_retrans(r)); 2579238104Sdes fprintf(output, "fallback: %d\n", ldns_resolver_fallback(r)); 2580238104Sdes fprintf(output, "random: %d\n", ldns_resolver_random(r)); 2581238104Sdes fprintf(output, "timeout: %d\n", (int)ldns_resolver_timeout(r).tv_sec); 2582238104Sdes fprintf(output, "dnssec: %d\n", ldns_resolver_dnssec(r)); 2583238104Sdes fprintf(output, "dnssec cd: %d\n", ldns_resolver_dnssec_cd(r)); 2584238104Sdes fprintf(output, "trust anchors (%d listed):\n", 2585238104Sdes (int)ldns_rr_list_rr_count(ldns_resolver_dnssec_anchors(r))); 2586238104Sdes ldns_rr_list_print_fmt(output, fmt, ldns_resolver_dnssec_anchors(r)); 2587238104Sdes fprintf(output, "tsig: %s %s\n", 2588238104Sdes ldns_resolver_tsig_keyname(r)?ldns_resolver_tsig_keyname(r):"-", 2589238104Sdes ldns_resolver_tsig_algorithm(r)?ldns_resolver_tsig_algorithm(r):"-"); 2590238104Sdes fprintf(output, "debug: %d\n", ldns_resolver_debug(r)); 2591238104Sdes 2592238104Sdes fprintf(output, "default domain: "); 2593238104Sdes ldns_rdf_print(output, ldns_resolver_domain(r)); 2594238104Sdes fprintf(output, "\n"); 2595238104Sdes fprintf(output, "apply default domain: %d\n", ldns_resolver_defnames(r)); 2596238104Sdes 2597238104Sdes fprintf(output, "searchlist (%d listed):\n", (int)ldns_resolver_searchlist_count(r)); 2598238104Sdes for (i = 0; i < ldns_resolver_searchlist_count(r); i++) { 2599238104Sdes fprintf(output, "\t"); 2600238104Sdes ldns_rdf_print(output, s[i]); 2601238104Sdes fprintf(output, "\n"); 2602238104Sdes } 2603238104Sdes fprintf(output, "apply search list: %d\n", ldns_resolver_dnsrch(r)); 2604238104Sdes 2605238104Sdes fprintf(output, "nameservers (%d listed):\n", (int)ldns_resolver_nameserver_count(r)); 2606238104Sdes for (i = 0; i < ldns_resolver_nameserver_count(r); i++) { 2607238104Sdes fprintf(output, "\t"); 2608238104Sdes ldns_rdf_print(output, n[i]); 2609238104Sdes 2610238104Sdes switch ((int)rtt[i]) { 2611238104Sdes case LDNS_RESOLV_RTT_MIN: 2612238104Sdes fprintf(output, " - reachable\n"); 2613238104Sdes break; 2614238104Sdes case LDNS_RESOLV_RTT_INF: 2615238104Sdes fprintf(output, " - unreachable\n"); 2616238104Sdes break; 2617238104Sdes } 2618238104Sdes } 2619238104Sdes} 2620238104Sdes 2621238104Sdesvoid 2622238104Sdesldns_resolver_print(FILE *output, const ldns_resolver *r) 2623238104Sdes{ 2624238104Sdes ldns_resolver_print_fmt(output, ldns_output_format_default, r); 2625238104Sdes} 2626238104Sdes 2627238104Sdesvoid 2628238104Sdesldns_zone_print_fmt(FILE *output, 2629238104Sdes const ldns_output_format *fmt, const ldns_zone *z) 2630238104Sdes{ 2631238104Sdes if(ldns_zone_soa(z)) 2632238104Sdes ldns_rr_print_fmt(output, fmt, ldns_zone_soa(z)); 2633238104Sdes ldns_rr_list_print_fmt(output, fmt, ldns_zone_rrs(z)); 2634238104Sdes} 2635238104Sdesvoid 2636238104Sdesldns_zone_print(FILE *output, const ldns_zone *z) 2637238104Sdes{ 2638238104Sdes ldns_zone_print_fmt(output, ldns_output_format_default, z); 2639238104Sdes} 2640