Example #1
0
void
log_nametypeclass(enum verbosity_value v, const char* str, uint8_t* name, 
	uint16_t type, uint16_t dclass)
{
	char buf[LDNS_MAX_DOMAINLEN+1];
	char t[12], c[12];
	const char *ts, *cs; 
	if(verbosity < v)
		return;
	dname_str(name, buf);
	if(type == LDNS_RR_TYPE_TSIG) ts = "TSIG";
	else if(type == LDNS_RR_TYPE_IXFR) ts = "IXFR";
	else if(type == LDNS_RR_TYPE_AXFR) ts = "AXFR";
	else if(type == LDNS_RR_TYPE_MAILB) ts = "MAILB";
	else if(type == LDNS_RR_TYPE_MAILA) ts = "MAILA";
	else if(type == LDNS_RR_TYPE_ANY) ts = "ANY";
	else if(ldns_rr_descript(type) && ldns_rr_descript(type)->_name)
		ts = ldns_rr_descript(type)->_name;
	else {
		snprintf(t, sizeof(t), "TYPE%d", (int)type);
		ts = t;
	}
	if(ldns_lookup_by_id(ldns_rr_classes, (int)dclass) &&
		ldns_lookup_by_id(ldns_rr_classes, (int)dclass)->name)
		cs = ldns_lookup_by_id(ldns_rr_classes, (int)dclass)->name;
	else {
		snprintf(c, sizeof(c), "CLASS%d", (int)dclass);
		cs = c;
	}
	log_info("%s %s %s %s", str, buf, ts, cs);
}
Example #2
0
/** return true if type needs domain name compression in rdata */
static const ldns_rr_descriptor*
type_rdata_compressable(struct ub_packed_rrset_key* key)
{
	uint16_t t = ntohs(key->rk.type);
	if(ldns_rr_descript(t) && 
		ldns_rr_descript(t)->_compress == LDNS_RR_COMPRESS)
		return ldns_rr_descript(t);
	return 0;
}
/** analyze rr in packet */
static void analyze_rr(ldns_buffer* pkt, int q)
{
	uint16_t type, dclass, len;
	uint32_t ttl;
	analyze_dname(pkt);
	type = ldns_buffer_read_u16(pkt);
	dclass = ldns_buffer_read_u16(pkt);
	printf("type %s(%d)", ldns_rr_descript(type)?  
		ldns_rr_descript(type)->_name: "??" , (int)type);
	printf(" class %s(%d) ", ldns_lookup_by_id(ldns_rr_classes, 
		(int)dclass)?ldns_lookup_by_id( ldns_rr_classes, 
		(int)dclass)->name:"??", (int)dclass);
	if(q) {
		printf("\n");
	} else {
		ttl = ldns_buffer_read_u32(pkt);
		printf(" ttl %d (0x%x)", (int)ttl, (unsigned)ttl);
		len = ldns_buffer_read_u16(pkt);
		printf(" rdata len %d:\n", (int)len);
		if(ldns_rr_descript(type))
			analyze_rdata(pkt, ldns_rr_descript(type), len);
		else ldns_buffer_skip(pkt, (ssize_t)len);
	}
}
Example #4
0
int
main(int argc, char **argv)
{
	char *filename;
	FILE *fp;
	ldns_zone *z;
	int line_nr = 0;
	int c;
	bool canonicalize = false;
	bool sort = false;
	bool strip = false;
	bool only_dnssec = false;
	bool print_soa = true;
	ldns_status s;
	size_t i;
	ldns_rr_list *stripped_list;
	ldns_rr *cur_rr;
	ldns_rr_type cur_rr_type;
	ldns_output_format_storage fmt_storage;
	ldns_output_format* fmt = ldns_output_format_init(&fmt_storage);

	ldns_soa_serial_increment_func_t soa_serial_increment_func = NULL;
	int soa_serial_increment_func_data = 0;

        while ((c = getopt(argc, argv, "0bcdhnpsu:U:vzS:")) != -1) {
                switch(c) {
			case 'b':
				fmt->flags |= 
					( LDNS_COMMENT_BUBBLEBABBLE |
					  LDNS_COMMENT_FLAGS        );
				break;
			case '0':
				fmt->flags |= LDNS_FMT_ZEROIZE_RRSIGS;
				break;
                	case 'c':
                		canonicalize = true;
                		break;
                	case 'd':
                		only_dnssec = true;
                		if (strip) {
                			fprintf(stderr, "Warning: stripping both DNSSEC and non-DNSSEC records. Output will be sparse.\n");
				}
				break;
			case 'h':
				print_usage("ldns-read-zone");
				break;
			case 'n':
				print_soa = false;
				break;
			case 'p':
				fmt->flags |= LDNS_FMT_PAD_SOA_SERIAL;
				break;
                        case 's':
                        	strip = true;
                		if (only_dnssec) {
                			fprintf(stderr, "Warning: stripping both DNSSEC and non-DNSSEC records. Output will be sparse.\n");
				}
                        	break;
			case 'u':
				s = ldns_output_format_set_type(fmt,
					ldns_get_rr_type_by_name(optarg));
				if (s != LDNS_STATUS_OK) {
					fprintf( stderr
					       , "Cannot set rr type %s "
					         "in output format to "
						 "print as unknown type: %s\n"
					       , ldns_rr_descript(
					       ldns_get_rr_type_by_name(optarg)
						       )->_name
					       , ldns_get_errorstr_by_id(s)
					       );
					exit(EXIT_FAILURE);
				}
				break;
			case 'U':
				s = ldns_output_format_clear_type(fmt,
					ldns_get_rr_type_by_name(optarg));
				if (s != LDNS_STATUS_OK) {
					fprintf( stderr
					       , "Cannot set rr type %s "
					         "in output format to not "
						 "print as unknown type: %s\n"
					       , ldns_rr_descript(
					       ldns_get_rr_type_by_name(optarg)
						       )->_name
					       , ldns_get_errorstr_by_id(s)
					       );
					exit(EXIT_FAILURE);
				}
				break;
			case 'v':
				printf("read zone version %s (ldns version %s)\n", LDNS_VERSION, ldns_version());
				exit(EXIT_SUCCESS);
				break;
                        case 'z':
                		canonicalize = true;
                                sort = true;
                                break;
			case 'S':
				strip = true;
				if (*optarg == '+' || *optarg == '-') {
					soa_serial_increment_func_data =
						atoi(optarg);
					soa_serial_increment_func =
						ldns_soa_serial_increment_by;
				} else if (! strtok(optarg, "0123456789")) {
					soa_serial_increment_func_data =
						atoi(optarg);
					soa_serial_increment_func =
						ldns_soa_serial_identity;
				} else if (!strcasecmp(optarg, "YYYYMMDDxx")){
					soa_serial_increment_func =
						ldns_soa_serial_datecounter;
				} else if (!strcasecmp(optarg, "unixtime")){
					soa_serial_increment_func =
						ldns_soa_serial_unixtime;
				} else {
					fprintf(stderr, "-S expects a number "
						"optionally preceded by a "
						"+ or - sign to indicate an "
						"offset, or the text YYYYMM"
						"DDxx or unixtime\n");
					exit(EXIT_FAILURE);
				}
				break;
		}
	}

	argc -= optind;
	argv += optind;

	if (argc == 0) {
		fp = stdin;
	} else {
		filename = argv[0];

		fp = fopen(filename, "r");
		if (!fp) {
			fprintf(stderr, "Unable to open %s: %s\n", filename, strerror(errno));
			exit(EXIT_FAILURE);
		}
	}
	
	s = ldns_zone_new_frm_fp_l(&z, fp, NULL, 0, LDNS_RR_CLASS_IN, &line_nr);

	fclose(fp);
	if (s != LDNS_STATUS_OK) {
		fprintf(stderr, "%s at %d\n", 
				ldns_get_errorstr_by_id(s),
				line_nr);
                exit(EXIT_FAILURE);
	}


	if (strip) {
		stripped_list = ldns_rr_list_new();
		while ((cur_rr = ldns_rr_list_pop_rr(ldns_zone_rrs(z)))) {
			cur_rr_type = ldns_rr_get_type(cur_rr);
			if (cur_rr_type == LDNS_RR_TYPE_RRSIG ||
			    cur_rr_type == LDNS_RR_TYPE_NSEC ||
			    cur_rr_type == LDNS_RR_TYPE_NSEC3 ||
			    cur_rr_type == LDNS_RR_TYPE_NSEC3PARAM
			   ) {
				ldns_rr_free(cur_rr);
			} else {
				ldns_rr_list_push_rr(stripped_list, cur_rr);
			}
		}
		ldns_rr_list_free(ldns_zone_rrs(z));
		ldns_zone_set_rrs(z, stripped_list);
	}
	if (only_dnssec) {
		stripped_list = ldns_rr_list_new();
		while ((cur_rr = ldns_rr_list_pop_rr(ldns_zone_rrs(z)))) {
			cur_rr_type = ldns_rr_get_type(cur_rr);
			if (cur_rr_type == LDNS_RR_TYPE_RRSIG ||
			    cur_rr_type == LDNS_RR_TYPE_NSEC ||
			    cur_rr_type == LDNS_RR_TYPE_NSEC3 ||
			    cur_rr_type == LDNS_RR_TYPE_NSEC3PARAM
			   ) {
				ldns_rr_list_push_rr(stripped_list, cur_rr);
			} else {
				ldns_rr_free(cur_rr);
			}
		}
		ldns_rr_list_free(ldns_zone_rrs(z));
		ldns_zone_set_rrs(z, stripped_list);
	}

	if (canonicalize) {
		ldns_rr2canonical(ldns_zone_soa(z));
		for (i = 0; i < ldns_rr_list_rr_count(ldns_zone_rrs(z)); i++) {
			ldns_rr2canonical(ldns_rr_list_rr(ldns_zone_rrs(z), i));
		}
	}
	if (sort) {
		ldns_zone_sort(z);
	}

	if (print_soa && ldns_zone_soa(z)) {
		if (soa_serial_increment_func) {
			ldns_rr_soa_increment_func_int(
					ldns_zone_soa(z)
				, soa_serial_increment_func
				, soa_serial_increment_func_data
				);
		}
		ldns_rr_print_fmt(stdout, fmt, ldns_zone_soa(z));
	}
	ldns_rr_list_print_fmt(stdout, fmt, ldns_zone_rrs(z));

	ldns_zone_deep_free(z);

        exit(EXIT_SUCCESS);
}
Example #5
0
/** print extended stats */
static int
print_ext(SSL* ssl, struct stats_info* s)
{
	int i;
	char nm[16];
	const ldns_rr_descriptor* desc;
	const ldns_lookup_table* lt;
	/* TYPE */
	for(i=0; i<STATS_QTYPE_NUM; i++) {
		if(inhibit_zero && s->svr.qtype[i] == 0)
			continue;
		desc = ldns_rr_descript((uint16_t)i);
		if(desc && desc->_name) {
			snprintf(nm, sizeof(nm), "%s", desc->_name);
		} else if (i == LDNS_RR_TYPE_IXFR) {
			snprintf(nm, sizeof(nm), "IXFR");
		} else if (i == LDNS_RR_TYPE_AXFR) {
			snprintf(nm, sizeof(nm), "AXFR");
		} else if (i == LDNS_RR_TYPE_MAILA) {
			snprintf(nm, sizeof(nm), "MAILA");
		} else if (i == LDNS_RR_TYPE_MAILB) {
			snprintf(nm, sizeof(nm), "MAILB");
		} else if (i == LDNS_RR_TYPE_ANY) {
			snprintf(nm, sizeof(nm), "ANY");
		} else {
			snprintf(nm, sizeof(nm), "TYPE%d", i);
		}
		if(!ssl_printf(ssl, "num.query.type.%s"SQ"%u\n", 
			nm, (unsigned)s->svr.qtype[i])) return 0;
	}
	if(!inhibit_zero || s->svr.qtype_big) {
		if(!ssl_printf(ssl, "num.query.type.other"SQ"%u\n", 
			(unsigned)s->svr.qtype_big)) return 0;
	}
	/* CLASS */
	for(i=0; i<STATS_QCLASS_NUM; i++) {
		if(inhibit_zero && s->svr.qclass[i] == 0)
			continue;
		lt = ldns_lookup_by_id(ldns_rr_classes, i);
		if(lt && lt->name) {
			snprintf(nm, sizeof(nm), "%s", lt->name);
		} else {
			snprintf(nm, sizeof(nm), "CLASS%d", i);
		}
		if(!ssl_printf(ssl, "num.query.class.%s"SQ"%u\n", 
			nm, (unsigned)s->svr.qclass[i])) return 0;
	}
	if(!inhibit_zero || s->svr.qclass_big) {
		if(!ssl_printf(ssl, "num.query.class.other"SQ"%u\n", 
			(unsigned)s->svr.qclass_big)) return 0;
	}
	/* OPCODE */
	for(i=0; i<STATS_OPCODE_NUM; i++) {
		if(inhibit_zero && s->svr.qopcode[i] == 0)
			continue;
		lt = ldns_lookup_by_id(ldns_opcodes, i);
		if(lt && lt->name) {
			snprintf(nm, sizeof(nm), "%s", lt->name);
		} else {
			snprintf(nm, sizeof(nm), "OPCODE%d", i);
		}
		if(!ssl_printf(ssl, "num.query.opcode.%s"SQ"%u\n", 
			nm, (unsigned)s->svr.qopcode[i])) return 0;
	}
	/* transport */
	if(!ssl_printf(ssl, "num.query.tcp"SQ"%u\n", 
		(unsigned)s->svr.qtcp)) return 0;
	if(!ssl_printf(ssl, "num.query.ipv6"SQ"%u\n", 
		(unsigned)s->svr.qipv6)) return 0;
	/* flags */
	if(!ssl_printf(ssl, "num.query.flags.QR"SQ"%u\n", 
		(unsigned)s->svr.qbit_QR)) return 0;
	if(!ssl_printf(ssl, "num.query.flags.AA"SQ"%u\n", 
		(unsigned)s->svr.qbit_AA)) return 0;
	if(!ssl_printf(ssl, "num.query.flags.TC"SQ"%u\n", 
		(unsigned)s->svr.qbit_TC)) return 0;
	if(!ssl_printf(ssl, "num.query.flags.RD"SQ"%u\n", 
		(unsigned)s->svr.qbit_RD)) return 0;
	if(!ssl_printf(ssl, "num.query.flags.RA"SQ"%u\n", 
		(unsigned)s->svr.qbit_RA)) return 0;
	if(!ssl_printf(ssl, "num.query.flags.Z"SQ"%u\n", 
		(unsigned)s->svr.qbit_Z)) return 0;
	if(!ssl_printf(ssl, "num.query.flags.AD"SQ"%u\n", 
		(unsigned)s->svr.qbit_AD)) return 0;
	if(!ssl_printf(ssl, "num.query.flags.CD"SQ"%u\n", 
		(unsigned)s->svr.qbit_CD)) return 0;
	if(!ssl_printf(ssl, "num.query.edns.present"SQ"%u\n", 
		(unsigned)s->svr.qEDNS)) return 0;
	if(!ssl_printf(ssl, "num.query.edns.DO"SQ"%u\n", 
		(unsigned)s->svr.qEDNS_DO)) return 0;

	/* RCODE */
	for(i=0; i<STATS_RCODE_NUM; i++) {
		if(inhibit_zero && s->svr.ans_rcode[i] == 0)
			continue;
		lt = ldns_lookup_by_id(ldns_rcodes, i);
		if(lt && lt->name) {
			snprintf(nm, sizeof(nm), "%s", lt->name);
		} else {
			snprintf(nm, sizeof(nm), "RCODE%d", i);
		}
		if(!ssl_printf(ssl, "num.answer.rcode.%s"SQ"%u\n", 
			nm, (unsigned)s->svr.ans_rcode[i])) return 0;
	}
	if(!inhibit_zero || s->svr.ans_rcode_nodata) {
		if(!ssl_printf(ssl, "num.answer.rcode.nodata"SQ"%u\n", 
			(unsigned)s->svr.ans_rcode_nodata)) return 0;
	}
	/* validation */
	if(!ssl_printf(ssl, "num.answer.secure"SQ"%u\n", 
		(unsigned)s->svr.ans_secure)) return 0;
	if(!ssl_printf(ssl, "num.answer.bogus"SQ"%u\n", 
		(unsigned)s->svr.ans_bogus)) return 0;
	if(!ssl_printf(ssl, "num.rrset.bogus"SQ"%u\n", 
		(unsigned)s->svr.rrset_bogus)) return 0;
	/* threat detection */
	if(!ssl_printf(ssl, "unwanted.queries"SQ"%u\n", 
		(unsigned)s->svr.unwanted_queries)) return 0;
	if(!ssl_printf(ssl, "unwanted.replies"SQ"%u\n", 
		(unsigned)s->svr.unwanted_replies)) return 0;
	return 1;
}
Example #6
0
ldns_status
do_chase(ldns_resolver *res,
	    ldns_rdf *name,
	    ldns_rr_type type,
	    ldns_rr_class c,
	    ldns_rr_list *trusted_keys,
	    ldns_pkt *pkt_o,
	    uint16_t qflags,
	    ldns_rr_list *prev_key_list,
	    int verbosity)
{
	ldns_rr_list *rrset = NULL;
	ldns_status result;
	ldns_rr *orig_rr = NULL;
	
/*
	ldns_rr_list *sigs;
	ldns_rr *cur_sig;
	uint16_t sig_i;
	ldns_rr_list *keys;
*/
	ldns_pkt *pkt;
	ldns_status tree_result;
	ldns_dnssec_data_chain *chain;
	ldns_dnssec_trust_tree *tree;
	
	const ldns_rr_descriptor *descriptor;
	descriptor = ldns_rr_descript(type);

	ldns_dname2canonical(name);
	
	pkt = ldns_pkt_clone(pkt_o);
	if (!name) {
		ldns_pkt_free(pkt);
		return LDNS_STATUS_EMPTY_LABEL;
	}
	if (verbosity != -1) {
		printf(";; Chasing: ");
			ldns_rdf_print(stdout, name);
			if (descriptor && descriptor->_name) {
				printf(" %s\n", descriptor->_name);
			} else {
				printf(" type %d\n", type);
			}
	}

	if (!trusted_keys || ldns_rr_list_rr_count(trusted_keys) < 1) {
	}
	
	if (pkt) {
		rrset = ldns_pkt_rr_list_by_name_and_type(pkt,
				name,
				type,
				LDNS_SECTION_ANSWER
				);
		if (!rrset) {
			/* nothing in answer, try authority */
			rrset = ldns_pkt_rr_list_by_name_and_type(pkt,
					name,
					type,
					LDNS_SECTION_AUTHORITY
					);
		}
		/* answer might be a cname, chase that first, then chase
		   cname target? (TODO) */
		if (!rrset) {
			rrset = ldns_pkt_rr_list_by_name_and_type(pkt,
					name,
					LDNS_RR_TYPE_CNAME,
					LDNS_SECTION_ANSWER
					);
			if (!rrset) {
				/* nothing in answer, try authority */
				rrset = ldns_pkt_rr_list_by_name_and_type(pkt,
						name,
						LDNS_RR_TYPE_CNAME,
						LDNS_SECTION_AUTHORITY
						);
			}
		}
	} else {
		/* no packet? */
		if (verbosity >= 0) {
			fprintf(stderr, "%s", ldns_get_errorstr_by_id(LDNS_STATUS_MEM_ERR));
			fprintf(stderr, "\n");
		}
		return LDNS_STATUS_MEM_ERR;
	}
	
	if (!rrset) {
		/* not found in original packet, try again */
		ldns_pkt_free(pkt);
		pkt = NULL;
		pkt = ldns_resolver_query(res, name, type, c, qflags);
		
		if (!pkt) {
			if (verbosity >= 0) {
				fprintf(stderr, "%s", ldns_get_errorstr_by_id(LDNS_STATUS_NETWORK_ERR));
				fprintf(stderr, "\n");
			}
			return LDNS_STATUS_NETWORK_ERR;
		}
		if (verbosity >= 5) {
			ldns_pkt_print(stdout, pkt);
		}
		
		rrset =	ldns_pkt_rr_list_by_name_and_type(pkt,
				name,
				type,
				LDNS_SECTION_ANSWER
				);
	}
	
	orig_rr = ldns_rr_new();

/* if the answer had no answer section, we need to construct our own rr (for instance if
 * the rr qe asked for doesn't exist. This rr will be destroyed when the chain is freed */
	if (ldns_pkt_ancount(pkt) < 1) {
		ldns_rr_set_type(orig_rr, type);
		ldns_rr_set_owner(orig_rr, ldns_rdf_clone(name));
	
		chain = ldns_dnssec_build_data_chain(res, qflags, rrset, pkt, ldns_rr_clone(orig_rr));
	} else {
		/* chase the first answer */
		chain = ldns_dnssec_build_data_chain(res, qflags, rrset, pkt, NULL);
	}

	if (verbosity >= 4) {
		printf("\n\nDNSSEC Data Chain:\n");
		ldns_dnssec_data_chain_print(stdout, chain);
	}
	
	result = LDNS_STATUS_OK;

	tree = ldns_dnssec_derive_trust_tree(chain, NULL);

	if (verbosity >= 2) {
		printf("\n\nDNSSEC Trust tree:\n");
		ldns_dnssec_trust_tree_print(stdout, tree, 0, true);
	}

	if (ldns_rr_list_rr_count(trusted_keys) > 0) {
		tree_result = ldns_dnssec_trust_tree_contains_keys(tree, trusted_keys);

		if (tree_result == LDNS_STATUS_DNSSEC_EXISTENCE_DENIED) {
			if (verbosity >= 1) {
				printf("Existence denied or verifiably insecure\n");
			}
			result = LDNS_STATUS_OK;
		} else if (tree_result != LDNS_STATUS_OK) {
			if (verbosity >= 1) {
				printf("No trusted keys found in tree: first error was: %s\n", ldns_get_errorstr_by_id(tree_result));
			}
			result = tree_result;
		}

	} else {
		result = -1;
		if (verbosity >= 0) {
			printf("You have not provided any trusted keys.\n");
		}
	}
	
	ldns_rr_free(orig_rr);
	ldns_dnssec_trust_tree_free(tree);
	ldns_dnssec_data_chain_deep_free(chain);
	
	ldns_rr_list_deep_free(rrset);
	ldns_pkt_free(pkt);
	/*	ldns_rr_free(orig_rr);*/

	return result;
}
Example #7
0
/*return hash name match*/
ldns_rr *
ldns_nsec3_exact_match(ldns_rdf *qname, ldns_rr_type qtype, ldns_rr_list *nsec3s) {
	uint8_t algorithm;
	uint32_t iterations;
	uint8_t salt_length;
	uint8_t *salt;
	
	ldns_rdf *sname, *hashed_sname;
	
	size_t nsec_i;
	ldns_rr *nsec;
	ldns_rr *result = NULL;
	
	ldns_status status;
	
	const ldns_rr_descriptor *descriptor;
	
	ldns_rdf *zone_name;
	
	if (verbosity >= 4) {
		printf(";; finding exact match for ");
		descriptor = ldns_rr_descript(qtype);
		if (descriptor && descriptor->_name) {
			printf("%s ", descriptor->_name);
		} else {
			printf("TYPE%d ", qtype);
		}
		ldns_rdf_print(stdout, qname);
		printf("\n");
	}
	
	if (!qname || !nsec3s || ldns_rr_list_rr_count(nsec3s) < 1) {
		if (verbosity >= 4) {
			printf("no qname, nsec3s or list empty\n");
		}
		return NULL;
	}

	nsec = ldns_rr_list_rr(nsec3s, 0);
	algorithm = ldns_nsec3_algorithm(nsec);
	salt_length = ldns_nsec3_salt_length(nsec);
	salt = ldns_nsec3_salt_data(nsec);
	iterations = ldns_nsec3_iterations(nsec);

	sname = ldns_rdf_clone(qname);

	if (verbosity >= 4) {
		printf(";; owner name hashes to: ");
	}
	hashed_sname = ldns_nsec3_hash_name(sname, algorithm, iterations, salt_length, salt);

	zone_name = ldns_dname_left_chop(ldns_rr_owner(nsec));
	status = ldns_dname_cat(hashed_sname, zone_name);
	
	if (verbosity >= 4) {
		ldns_rdf_print(stdout, hashed_sname);
		printf("\n");
	}

	for (nsec_i = 0; nsec_i < ldns_rr_list_rr_count(nsec3s); nsec_i++) {
		nsec = ldns_rr_list_rr(nsec3s, nsec_i);
		
		/* check values of iterations etc! */
		
		/* exact match? */
		if (ldns_dname_compare(ldns_rr_owner(nsec), hashed_sname) == 0) {
			result = nsec;
			goto done;
		}
		
	}

done:
	ldns_rdf_deep_free(zone_name);
	ldns_rdf_deep_free(sname);
	ldns_rdf_deep_free(hashed_sname);
	LDNS_FREE(salt);
	
	if (verbosity >= 4) {
		if (result) {
			printf(";; Found.\n");
		} else {
			printf(";; Not foud.\n");
		}
	}
	return result;
}
Example #8
0
/**
 * Compare two RRs in the same RRset and determine their relative
 * canonical order.
 * @param rrset: the rrset in which to perform compares.
 * @param i: first RR to compare
 * @param j: first RR to compare
 * @return 0 if RR i== RR j, -1 if <, +1 if >.
 */
static int
canonical_compare(struct ub_packed_rrset_key* rrset, size_t i, size_t j)
{
	struct packed_rrset_data* d = (struct packed_rrset_data*)
		rrset->entry.data;
	const ldns_rr_descriptor* desc;
	uint16_t type = ntohs(rrset->rk.type);
	size_t minlen;
	int c;

	if(i==j)
		return 0;
	/* in case rdata-len is to be compared for canonical order
	c = memcmp(d->rr_data[i], d->rr_data[j], 2);
	if(c != 0)
		return c; */

	switch(type) {
		/* These RR types have only a name as RDATA. 
		 * This name has to be canonicalized.*/
		case LDNS_RR_TYPE_NS:
		case LDNS_RR_TYPE_MD:
		case LDNS_RR_TYPE_MF:
		case LDNS_RR_TYPE_CNAME:
		case LDNS_RR_TYPE_MB:
		case LDNS_RR_TYPE_MG:
		case LDNS_RR_TYPE_MR:
		case LDNS_RR_TYPE_PTR:
		case LDNS_RR_TYPE_DNAME:
			return query_dname_compare(d->rr_data[i]+2, 
				d->rr_data[j]+2);

		/* These RR types have STR and fixed size rdata fields
		 * before one or more name fields that need canonicalizing,
		 * and after that a byte-for byte remainder can be compared.
		 */
		/* type starts with the name; remainder is binary compared */
		case LDNS_RR_TYPE_NXT: 
		/* use rdata field formats */
		case LDNS_RR_TYPE_MINFO:
		case LDNS_RR_TYPE_RP:
		case LDNS_RR_TYPE_SOA:
		case LDNS_RR_TYPE_RT:
		case LDNS_RR_TYPE_AFSDB:
		case LDNS_RR_TYPE_KX:
		case LDNS_RR_TYPE_MX:
		case LDNS_RR_TYPE_SIG:
		/* RRSIG signer name has to be downcased */
		case LDNS_RR_TYPE_RRSIG:
		case LDNS_RR_TYPE_PX:
		case LDNS_RR_TYPE_NAPTR:
		case LDNS_RR_TYPE_SRV:
			desc = ldns_rr_descript(type);
			log_assert(desc);
			/* this holds for the types that need canonicalizing */
			log_assert(desc->_minimum == desc->_maximum);
			return canonical_compare_byfield(d, desc, i, j);

		case LDNS_RR_TYPE_HINFO: /* no longer downcased */
		case LDNS_RR_TYPE_NSEC: 
	default:
		/* For unknown RR types, or types not listed above,
		 * no canonicalization is needed, do binary compare */
		/* byte for byte compare, equal means shortest first*/
		minlen = d->rr_len[i]-2;
		if(minlen > d->rr_len[j]-2)
			minlen = d->rr_len[j]-2;
		c = memcmp(d->rr_data[i]+2, d->rr_data[j]+2, minlen);
		if(c!=0)
			return c;
		/* rdata equal, shortest is first */
		if(d->rr_len[i] < d->rr_len[j])
			return -1;
		if(d->rr_len[i] > d->rr_len[j])
			return 1;
		/* rdata equal, length equal */
		break;
	}
	return 0;
}
Example #9
0
/** do the rdata copy */
static int
rdata_copy(ldns_buffer* pkt, struct packed_rrset_data* data, uint8_t* to, 
	struct rr_parse* rr, uint32_t* rr_ttl, uint16_t type)
{
	uint16_t pkt_len;
	const ldns_rr_descriptor* desc;

	*rr_ttl = ldns_read_uint32(rr->ttl_data);
	/* RFC 2181 Section 8. if msb of ttl is set treat as if zero. */
	if(*rr_ttl & 0x80000000U)
		*rr_ttl = 0;
	if(*rr_ttl < MIN_TTL)
		*rr_ttl = MIN_TTL;
	if(*rr_ttl < data->ttl)
		data->ttl = *rr_ttl;

	if(rr->outside_packet) {
		/* uncompressed already, only needs copy */
		memmove(to, rr->ttl_data+sizeof(uint32_t), rr->size);
		return 1;
	}

	ldns_buffer_set_position(pkt, (size_t)
		(rr->ttl_data - ldns_buffer_begin(pkt) + sizeof(uint32_t)));
	/* insert decompressed size into rdata len stored in memory */
	/* -2 because rdatalen bytes are not included. */
	pkt_len = htons(rr->size - 2);
	memmove(to, &pkt_len, sizeof(uint16_t));
	to += 2;
	/* read packet rdata len */
	pkt_len = ldns_buffer_read_u16(pkt);
	if(ldns_buffer_remaining(pkt) < pkt_len)
		return 0;
	desc = ldns_rr_descript(type);
	if(pkt_len > 0 && desc && desc->_dname_count > 0) {
		int count = (int)desc->_dname_count;
		int rdf = 0;
		size_t len;
		size_t oldpos;
		/* decompress dnames. */
		while(pkt_len > 0 && count) {
			switch(desc->_wireformat[rdf]) {
			case LDNS_RDF_TYPE_DNAME:
				oldpos = ldns_buffer_position(pkt);
				dname_pkt_copy(pkt, to, 
					ldns_buffer_current(pkt));
				to += pkt_dname_len(pkt);
				pkt_len -= ldns_buffer_position(pkt)-oldpos;
				count--;
				len = 0;
				break;
			case LDNS_RDF_TYPE_STR:
				len = ldns_buffer_current(pkt)[0] + 1;
				break;
			default:
				len = get_rdf_size(desc->_wireformat[rdf]);
				break;
			}
			if(len) {
				memmove(to, ldns_buffer_current(pkt), len);
				to += len;
				ldns_buffer_skip(pkt, (ssize_t)len);
				log_assert(len <= pkt_len);
				pkt_len -= len;
			}
			rdf++;
		}
	}
	/* copy remaining rdata */
	if(pkt_len >  0)
		memmove(to, ldns_buffer_current(pkt), pkt_len);
	
	return 1;
}