int main(int argc, char **argv) { dns_fixedname_t fixed; dns_name_t *name; isc_buffer_t buffer; isc_region_t region; isc_result_t result; unsigned char hash[NSEC3_MAX_HASH_LENGTH]; unsigned char salt[DNS_NSEC3_SALTSIZE]; unsigned char text[1024]; unsigned int hash_alg; unsigned int length; unsigned int iterations; unsigned int salt_length; if (argc != 5) usage(); if (strcmp(argv[1], "-") == 0) { salt_length = 0; salt[0] = 0; } else { isc_buffer_init(&buffer, salt, sizeof(salt)); result = isc_hex_decodestring(argv[1], &buffer); check_result(result, "isc_hex_decodestring(salt)"); salt_length = isc_buffer_usedlength(&buffer); if (salt_length > DNS_NSEC3_SALTSIZE) fatal("salt too long"); } hash_alg = atoi(argv[2]); if (hash_alg > 255U) fatal("hash algorithm too large"); iterations = atoi(argv[3]); if (iterations > 0xffffU) fatal("iterations to large"); dns_fixedname_init(&fixed); name = dns_fixedname_name(&fixed); isc_buffer_init(&buffer, argv[4], strlen(argv[4])); isc_buffer_add(&buffer, strlen(argv[4])); result = dns_name_fromtext(name, &buffer, dns_rootname, 0, NULL); check_result(result, "dns_name_fromtext() failed"); dns_name_downcase(name, name, NULL); length = isc_iterated_hash(hash, hash_alg, iterations, salt, salt_length, name->ndata, name->length); if (length == 0) fatal("isc_iterated_hash failed"); region.base = hash; region.length = length; isc_buffer_init(&buffer, text, sizeof(text)); isc_base32hexnp_totext(®ion, 1, "", &buffer); fprintf(stdout, "%.*s (salt=%s, hash=%u, iterations=%u)\n", (int)isc_buffer_usedlength(&buffer), text, argv[1], hash_alg, iterations); return(0); }
static inline isc_result_t totext_nsec3(ARGS_TOTEXT) { isc_region_t sr; unsigned int i, j; unsigned char hash; unsigned char flags; char buf[sizeof("TYPE65535")]; isc_uint32_t iterations; REQUIRE(rdata->type == dns_rdatatype_nsec3); REQUIRE(rdata->length != 0); dns_rdata_toregion(rdata, &sr); /* Hash */ hash = uint8_fromregion(&sr); isc_region_consume(&sr, 1); sprintf(buf, "%u ", hash); RETERR(str_totext(buf, target)); /* Flags */ flags = uint8_fromregion(&sr); isc_region_consume(&sr, 1); sprintf(buf, "%u ", flags); RETERR(str_totext(buf, target)); /* Iterations */ iterations = uint16_fromregion(&sr); isc_region_consume(&sr, 2); sprintf(buf, "%u ", iterations); RETERR(str_totext(buf, target)); /* Salt */ j = uint8_fromregion(&sr); isc_region_consume(&sr, 1); INSIST(j <= sr.length); if (j != 0) { i = sr.length; sr.length = j; RETERR(isc_hex_totext(&sr, 1, "", target)); sr.length = i - j; } else RETERR(str_totext("-", target)); if ((tctx->flags & DNS_STYLEFLAG_MULTILINE) != 0) RETERR(str_totext(" (", target)); RETERR(str_totext(tctx->linebreak, target)); /* Next hash */ j = uint8_fromregion(&sr); isc_region_consume(&sr, 1); INSIST(j <= sr.length); i = sr.length; sr.length = j; RETERR(isc_base32hexnp_totext(&sr, 1, "", target)); sr.length = i - j; if ((tctx->flags & DNS_STYLEFLAG_MULTILINE) == 0) RETERR(str_totext(" ", target)); RETERR(typemap_totext(&sr, tctx, target)); if ((tctx->flags & DNS_STYLEFLAG_MULTILINE) != 0) RETERR(str_totext(" )", target)); return (ISC_R_SUCCESS); }
static void nsec3hash(nsec3printer *nsec3print, const char *algostr, const char *flagstr, const char *iterstr, const char *saltstr, const char *domain) { dns_fixedname_t fixed; dns_name_t *name; isc_buffer_t buffer; isc_region_t region; isc_result_t result; unsigned char hash[NSEC3_MAX_HASH_LENGTH]; unsigned char salt[DNS_NSEC3_SALTSIZE]; unsigned char text[1024]; unsigned int hash_alg; unsigned int flags; unsigned int length; unsigned int iterations; unsigned int salt_length; const char dash[] = "-"; if (strcmp(saltstr, "-") == 0) { salt_length = 0; salt[0] = 0; } else { isc_buffer_init(&buffer, salt, sizeof(salt)); result = isc_hex_decodestring(saltstr, &buffer); check_result(result, "isc_hex_decodestring(salt)"); salt_length = isc_buffer_usedlength(&buffer); if (salt_length > DNS_NSEC3_SALTSIZE) fatal("salt too long"); if (salt_length == 0) saltstr = dash; } hash_alg = atoi(algostr); if (hash_alg > 255U) fatal("hash algorithm too large"); flags = flagstr == NULL ? 0 : atoi(flagstr); if (flags > 255U) fatal("flags too large"); iterations = atoi(iterstr); if (iterations > 0xffffU) fatal("iterations to large"); dns_fixedname_init(&fixed); name = dns_fixedname_name(&fixed); isc_buffer_constinit(&buffer, domain, strlen(domain)); isc_buffer_add(&buffer, strlen(domain)); result = dns_name_fromtext(name, &buffer, dns_rootname, 0, NULL); check_result(result, "dns_name_fromtext() failed"); dns_name_downcase(name, name, NULL); length = isc_iterated_hash(hash, hash_alg, iterations, salt, salt_length, name->ndata, name->length); if (length == 0) fatal("isc_iterated_hash failed"); region.base = hash; region.length = length; isc_buffer_init(&buffer, text, sizeof(text)); isc_base32hexnp_totext(®ion, 1, "", &buffer); isc_buffer_putuint8(&buffer, '\0'); nsec3print(hash_alg, flags, iterations, saltstr, domain, (char *)text); }