Ejemplo n.º 1
0
/*%
 * Set '*exists' to true iff the given name exists, to false otherwise.
 */
static isc_result_t
name_exists(dns_db_t *db, dns_dbversion_t *version, dns_name_t *name,
	    isc_boolean_t *exists)
{
	isc_result_t result;
	dns_dbnode_t *node = NULL;
	dns_rdatasetiter_t *iter = NULL;

	result = dns_db_findnode(db, name, ISC_FALSE, &node);
	if (result == ISC_R_NOTFOUND) {
		*exists = ISC_FALSE;
		return (ISC_R_SUCCESS);
	}
	if (result != ISC_R_SUCCESS)
		return (result);

	result = dns_db_allrdatasets(db, node, version,
				     (isc_stdtime_t) 0, &iter);
	if (result != ISC_R_SUCCESS)
		goto cleanup_node;

	result = dns_rdatasetiter_first(iter);
	if (result == ISC_R_SUCCESS) {
		*exists = ISC_TRUE;
	} else if (result == ISC_R_NOMORE) {
		*exists = ISC_FALSE;
		result = ISC_R_SUCCESS;
	} else
		*exists = ISC_FALSE;
	dns_rdatasetiter_destroy(&iter);

 cleanup_node:
	dns_db_detachnode(db, &node);
	return (result);
}
Ejemplo n.º 2
0
static void
allrdatasets(isc_assertioncallback_t callback) {
	isc_result_t result;
	dns_dbnode_t *node = NULL;
	dns_rdatasetiter_t *iterator = NULL;

	result = dns_test_begin(NULL, ISC_FALSE);
	ATF_REQUIRE_EQ(result, ISC_R_SUCCESS);

	setup_db();

	result = dns_db_findnode(db1, dns_rootname, ISC_FALSE, &node);
	ATF_REQUIRE_EQ(result, ISC_R_SUCCESS);

	isc_assertion_setcallback(callback);
	result = dns_db_allrdatasets(db1, node, VERSION(callback), 0,
				     &iterator);
	if (callback != NULL)
		atf_tc_fail("dns_db_allrdatasets did not assert");
	ATF_REQUIRE_EQ(result, ISC_R_SUCCESS);

	dns_rdatasetiter_destroy(&iterator);
	ATF_REQUIRE_EQ(iterator, NULL);

	dns_db_detachnode(db1, &node);
	ATF_REQUIRE_EQ(node, NULL);

	close_db();

	dns_test_end();
}
Ejemplo n.º 3
0
static isc_result_t
allrdatasets(dns_db_t *db, dns_dbnode_t *node, dns_dbversion_t *version,
	     isc_stdtime_t now, dns_rdatasetiter_t **iteratorp)
{
	ldapdb_t *ldapdb = (ldapdb_t *) db;

	REQUIRE(VALID_LDAPDB(ldapdb));

	return dns_db_allrdatasets(ldapdb->rbtdb, node, version, now, iteratorp);
}
Ejemplo n.º 4
0
Archivo: db.c Proyecto: pecharmin/bind9
static isc_result_t
allrdatasets(dns_db_t *db, dns_dbnode_t *node, dns_dbversion_t *version,
	     isc_stdtime_t now, dns_rdatasetiter_t **iteratorp)
{
	sampledb_t *sampledb = (sampledb_t *) db;

	REQUIRE(VALID_SAMPLEDB(sampledb));

	return (dns_db_allrdatasets(sampledb->rbtdb, node, version,
				    now, iteratorp));
}
Ejemplo n.º 5
0
static isc_result_t
check_hints(dns_db_t *db) {
	isc_result_t result;
	dns_rdataset_t rootns;
	dns_dbiterator_t *dbiter = NULL;
	dns_dbnode_t *node = NULL;
	isc_stdtime_t now;
	dns_fixedname_t fixname;
	dns_name_t *name;
	dns_rdatasetiter_t *rdsiter = NULL;

	isc_stdtime_get(&now);

	dns_fixedname_init(&fixname);
	name = dns_fixedname_name(&fixname);

	dns_rdataset_init(&rootns);
	(void)dns_db_find(db, dns_rootname, NULL, dns_rdatatype_ns, 0,
			  now, NULL, name, &rootns, NULL);
	result = dns_db_createiterator(db, 0, &dbiter);
	if (result != ISC_R_SUCCESS)
		goto cleanup;
	result = dns_dbiterator_first(dbiter);
	while (result == ISC_R_SUCCESS) {
		result = dns_dbiterator_current(dbiter, &node, name);
		if (result != ISC_R_SUCCESS)
			goto cleanup;
		result = dns_db_allrdatasets(db, node, NULL, now, &rdsiter);
		if (result != ISC_R_SUCCESS)
			goto cleanup;
		result = check_node(&rootns, name, rdsiter);
		if (result != ISC_R_SUCCESS)
			goto cleanup;
		dns_rdatasetiter_destroy(&rdsiter);
		dns_db_detachnode(db, &node);
		result = dns_dbiterator_next(dbiter);
	}
	if (result == ISC_R_NOMORE)
		result = ISC_R_SUCCESS;

 cleanup:
	if (dns_rdataset_isassociated(&rootns))
		dns_rdataset_disassociate(&rootns);
	if (rdsiter != NULL)
		dns_rdatasetiter_destroy(&rdsiter);
	if (node != NULL)
		dns_db_detachnode(db, &node);
	if (dbiter != NULL)
		dns_dbiterator_destroy(&dbiter);
	return (result);
}
Ejemplo n.º 6
0
static isc_result_t
db_rr_iterator_next(db_rr_iterator_t *it) {
	if (it->result != ISC_R_SUCCESS)
		return (it->result);

	INSIST(it->dbit != NULL);
	INSIST(it->node != NULL);
	INSIST(it->rdatasetit != NULL);

	it->result = dns_rdataset_next(&it->rdataset);
	if (it->result == ISC_R_NOMORE) {
		dns_rdataset_disassociate(&it->rdataset);
		it->result = dns_rdatasetiter_next(it->rdatasetit);
		/*
		 * The while loop body is executed more than once
		 * only when an empty dbnode needs to be skipped.
		 */
		while (it->result == ISC_R_NOMORE) {
			dns_rdatasetiter_destroy(&it->rdatasetit);
			dns_db_detachnode(it->db, &it->node);
			it->result = dns_dbiterator_next(it->dbit);
			if (it->result == ISC_R_NOMORE) {
				/* We are at the end of the entire database. */
				return (it->result);
			}
			if (it->result != ISC_R_SUCCESS)
				return (it->result);
			it->result = dns_dbiterator_current(it->dbit,
				    &it->node,
				    dns_fixedname_name(&it->fixedname));
			if (it->result != ISC_R_SUCCESS)
				return (it->result);
			it->result = dns_db_allrdatasets(it->db, it->node,
					 it->ver, it->now,
					 &it->rdatasetit);
			if (it->result != ISC_R_SUCCESS)
				return (it->result);
			it->result = dns_rdatasetiter_first(it->rdatasetit);
		}
		if (it->result != ISC_R_SUCCESS)
			return (it->result);
		dns_rdatasetiter_current(it->rdatasetit, &it->rdataset);
		it->rdataset.attributes |= DNS_RDATASETATTR_LOADORDER;
		it->result = dns_rdataset_first(&it->rdataset);
		if (it->result != ISC_R_SUCCESS)
			return (it->result);
	}
	return (it->result);
}
Ejemplo n.º 7
0
isc_result_t
dns_rriterator_first(dns_rriterator_t *it) {
	REQUIRE(VALID_RRITERATOR(it));
	/* Reset state */
	if (dns_rdataset_isassociated(&it->rdataset))
		dns_rdataset_disassociate(&it->rdataset);
	if (it->rdatasetit != NULL)
		dns_rdatasetiter_destroy(&it->rdatasetit);
	if (it->node != NULL)
		dns_db_detachnode(it->db, &it->node);
	it->result = dns_dbiterator_first(it->dbit);

	/*
	 * The top node may be empty when out of zone glue exists.
	 * Walk the tree to find the first node with data.
	 */
	while (it->result == ISC_R_SUCCESS) {
		it->result = dns_dbiterator_current(it->dbit, &it->node,
					   dns_fixedname_name(&it->fixedname));
		if (it->result != ISC_R_SUCCESS)
			return (it->result);

		it->result = dns_db_allrdatasets(it->db, it->node, it->ver,
						 it->now, &it->rdatasetit);
		if (it->result != ISC_R_SUCCESS)
			return (it->result);

		it->result = dns_rdatasetiter_first(it->rdatasetit);
		if (it->result != ISC_R_SUCCESS) {
			/*
			 * This node is empty. Try next node.
			 */
			dns_rdatasetiter_destroy(&it->rdatasetit);
			dns_db_detachnode(it->db, &it->node);
			it->result = dns_dbiterator_next(it->dbit);
			continue;
		}
		dns_rdatasetiter_current(it->rdatasetit, &it->rdataset);
		dns_rdataset_getownercase(&it->rdataset,
					  dns_fixedname_name(&it->fixedname));
		it->rdataset.attributes |= DNS_RDATASETATTR_LOADORDER;
		it->result = dns_rdataset_first(&it->rdataset);
		return (it->result);
	}
	return (it->result);
}
Ejemplo n.º 8
0
static inline isc_boolean_t active_node (dns_db_t * db, dns_dbversion_t * version, dns_dbnode_t * node)
{
    dns_rdatasetiter_t *rdsiter;

    isc_boolean_t active = ISC_FALSE;

    isc_result_t result;

    dns_rdataset_t rdataset;

    dns_rdataset_init (&rdataset);
    rdsiter = NULL;
    result = dns_db_allrdatasets (db, node, version, 0, &rdsiter);
    check_result (result, "dns_db_allrdatasets()");
    result = dns_rdatasetiter_first (rdsiter);
    while (result == ISC_R_SUCCESS)
    {
        dns_rdatasetiter_current (rdsiter, &rdataset);
        if (rdataset.type != dns_rdatatype_nsec)
            active = ISC_TRUE;
        dns_rdataset_disassociate (&rdataset);
        if (!active)
            result = dns_rdatasetiter_next (rdsiter);
        else
            result = ISC_R_NOMORE;
    }
    if (result != ISC_R_NOMORE)
        fatal ("rdataset iteration failed");
    dns_rdatasetiter_destroy (&rdsiter);

    if (!active)
    {
        /*
         * Make sure there is no NSEC record for this node.
         */
        result = dns_db_deleterdataset (db, node, version, dns_rdatatype_nsec, 0);
        if (result == DNS_R_UNCHANGED)
            result = ISC_R_SUCCESS;
        check_result (result, "dns_db_deleterdataset");
    }

    return (active);
}
Ejemplo n.º 9
0
static isc_result_t
node_isempty(dns_db_t *db, dns_dbnode_t *node, dns_dbversion_t *version,
	     isc_stdtime_t now, isc_boolean_t *isempty) {
	dns_rdatasetiter_t *rds_iter = NULL;
	dns_fixedname_t fname;
	char buff[DNS_NAME_FORMATSIZE];
	isc_result_t result;

	dns_fixedname_init(&fname);

	CHECK(ldapdb_name_fromnode(node, dns_fixedname_name(&fname)));

	result = dns_db_allrdatasets(db, node, version, now, &rds_iter);
	if (result == ISC_R_NOTFOUND) {
		*isempty = ISC_TRUE;
	} else if (result == ISC_R_SUCCESS) {
		result = dns_rdatasetiter_first(rds_iter);
		if (result == ISC_R_NOMORE) {
			*isempty = ISC_TRUE;
			result = ISC_R_SUCCESS;
		} else if (result == ISC_R_SUCCESS) {
			*isempty = ISC_FALSE;
			result = ISC_R_SUCCESS;
		} else if (result != ISC_R_SUCCESS) {
			dns_name_format(dns_fixedname_name(&fname),
					buff, DNS_NAME_FORMATSIZE);
			log_error_r("dns_rdatasetiter_first() failed during "
				    "node_isempty() for name '%s'", buff);
		}
		dns_rdatasetiter_destroy(&rds_iter);
	} else {
		dns_name_format(dns_fixedname_name(&fname),
				buff, DNS_NAME_FORMATSIZE);
		log_error_r("dns_db_allrdatasets() failed during "
			    "node_isempty() for name '%s'", buff);
	}

cleanup:
	return result;
}
Ejemplo n.º 10
0
isc_result_t
dns_rriterator_nextrrset(dns_rriterator_t *it) {
	REQUIRE(VALID_RRITERATOR(it));
	if (dns_rdataset_isassociated(&it->rdataset))
		dns_rdataset_disassociate(&it->rdataset);
	it->result = dns_rdatasetiter_next(it->rdatasetit);
	/*
	 * The while loop body is executed more than once
	 * only when an empty dbnode needs to be skipped.
	 */
	while (it->result == ISC_R_NOMORE) {
		dns_rdatasetiter_destroy(&it->rdatasetit);
		dns_db_detachnode(it->db, &it->node);
		it->result = dns_dbiterator_next(it->dbit);
		if (it->result == ISC_R_NOMORE) {
			/* We are at the end of the entire database. */
			return (it->result);
		}
		if (it->result != ISC_R_SUCCESS)
			return (it->result);
		it->result = dns_dbiterator_current(it->dbit, &it->node,
					   dns_fixedname_name(&it->fixedname));
		if (it->result != ISC_R_SUCCESS)
			return (it->result);
		it->result = dns_db_allrdatasets(it->db, it->node, it->ver,
						 it->now, &it->rdatasetit);
		if (it->result != ISC_R_SUCCESS)
			return (it->result);
		it->result = dns_rdatasetiter_first(it->rdatasetit);
	}
	if (it->result != ISC_R_SUCCESS)
		return (it->result);
	dns_rdatasetiter_current(it->rdatasetit, &it->rdataset);
	dns_rdataset_getownercase(&it->rdataset,
				  dns_fixedname_name(&it->fixedname));
	it->rdataset.attributes |= DNS_RDATASETATTR_LOADORDER;
	it->result = dns_rdataset_first(&it->rdataset);
	return (it->result);
}
Ejemplo n.º 11
0
static isc_result_t
db_rr_iterator_first(db_rr_iterator_t *it) {
	it->result = dns_dbiterator_first(it->dbit);
	/*
	 * The top node may be empty when out of zone glue exists.
	 * Walk the tree to find the first node with data.
	 */
	while (it->result == ISC_R_SUCCESS) {
		it->result = dns_dbiterator_current(it->dbit, &it->node,
				    dns_fixedname_name(&it->fixedname));
		if (it->result != ISC_R_SUCCESS)
			return (it->result);

		it->result = dns_db_allrdatasets(it->db, it->node,
						 it->ver, it->now,
						 &it->rdatasetit);
		if (it->result != ISC_R_SUCCESS)
			return (it->result);

		it->result = dns_rdatasetiter_first(it->rdatasetit);
		if (it->result != ISC_R_SUCCESS) {
			/*
			 * This node is empty. Try next node.
			 */
			dns_rdatasetiter_destroy(&it->rdatasetit);
			dns_db_detachnode(it->db, &it->node);
			it->result = dns_dbiterator_next(it->dbit);
			continue;
		}
		dns_rdatasetiter_current(it->rdatasetit, &it->rdataset);
		it->rdataset.attributes |= DNS_RDATASETATTR_LOADORDER;
		it->result = dns_rdataset_first(&it->rdataset);
		return (it->result);
	}
	return (it->result);
}
Ejemplo n.º 12
0
int
main(int argc, char *argv[]) {
	dns_db_t *db;
	dns_dbnode_t *node;
	isc_result_t result;
	dns_name_t name;
	dns_offsets_t offsets;
	size_t len;
	isc_buffer_t source, target;
	char s[1000];
	char b[255];
	dns_rdataset_t rdataset, sigrdataset;
	int ch;
	dns_rdatatype_t type = 1;
	isc_boolean_t printnode = ISC_FALSE;
	isc_boolean_t addmode = ISC_FALSE;
	isc_boolean_t delmode = ISC_FALSE;
	isc_boolean_t holdmode = ISC_FALSE;
	isc_boolean_t verbose = ISC_FALSE;
	isc_boolean_t done = ISC_FALSE;
	isc_boolean_t quiet = ISC_FALSE;
	isc_boolean_t time_lookups = ISC_FALSE;
	isc_boolean_t found_as;
	isc_boolean_t find_zonecut = ISC_FALSE;
	isc_boolean_t noexact_zonecut = ISC_FALSE;
	int i, v;
	dns_rdatasetiter_t *rdsiter;
	char t1[256];
	char t2[256];
	isc_buffer_t tb1, tb2;
	isc_region_t r1, r2;
	dns_fixedname_t foundname;
	dns_name_t *fname;
	unsigned int options = 0, zcoptions;
	isc_time_t start, finish;
	char *origintext;
	dbinfo *dbi;
	dns_dbversion_t *version;
	dns_name_t *origin;
	size_t memory_quota = 0;
	dns_trust_t trust = 0;
	unsigned int addopts;
	isc_log_t *lctx = NULL;
	size_t n;

	dns_result_register();

	RUNTIME_CHECK(isc_mem_create(0, 0, &mctx) == ISC_R_SUCCESS);
	RUNTIME_CHECK(dns_dbtable_create(mctx, dns_rdataclass_in, &dbtable) ==
		      ISC_R_SUCCESS);



	strcpy(dbtype, "rbt");
	while ((ch = isc_commandline_parse(argc, argv, "c:d:t:z:P:Q:glpqvT"))
	       != -1) {
		switch (ch) {
		case 'c':
			result = load(isc_commandline_argument, ".", ISC_TRUE);
			if (result != ISC_R_SUCCESS)
				printf("cache load(%s) %08x: %s\n",
				       isc_commandline_argument, result,
				       isc_result_totext(result));
			break;
		case 'd':
			n = strlcpy(dbtype, isc_commandline_argument,
				    sizeof(dbtype));
			if (n >= sizeof(dbtype)) {
				fprintf(stderr, "bad db type '%s'\n",
					isc_commandline_argument);
				exit(1);
			}
			break;
		case 'g':
			options |= (DNS_DBFIND_GLUEOK|DNS_DBFIND_VALIDATEGLUE);
			break;
		case 'l':
			RUNTIME_CHECK(isc_log_create(mctx, &lctx,
						     NULL) == ISC_R_SUCCESS);
			isc_log_setcontext(lctx);
			dns_log_init(lctx);
			dns_log_setcontext(lctx);
			break;
		case 'q':
			quiet = ISC_TRUE;
			verbose = ISC_FALSE;
			break;
		case 'p':
			printnode = ISC_TRUE;
			break;
		case 'P':
			pause_every = atoi(isc_commandline_argument);
			break;
		case 'Q':
			memory_quota = atoi(isc_commandline_argument);
			isc_mem_setquota(mctx, memory_quota);
			break;
		case 't':
			type = atoi(isc_commandline_argument);
			break;
		case 'T':
			time_lookups = ISC_TRUE;
			break;
		case 'v':
			verbose = ISC_TRUE;
			break;
		case 'z':
			origintext = strrchr(isc_commandline_argument, '/');
			if (origintext == NULL)
				origintext = isc_commandline_argument;
			else
				origintext++;	/* Skip '/'. */
			result = load(isc_commandline_argument, origintext,
				      ISC_FALSE);
			if (result != ISC_R_SUCCESS)
				printf("zone load(%s) %08x: %s\n",
				       isc_commandline_argument, result,
				       isc_result_totext(result));
			break;
		}
	}

	argc -= isc_commandline_index;
	argv += isc_commandline_index;
	POST(argv);

	if (argc != 0)
		printf("ignoring trailing arguments\n");

	/*
	 * Some final initialization...
	 */
	dns_fixedname_init(&foundname);
	fname = dns_fixedname_name(&foundname);
	dbi = NULL;
	origin = dns_rootname;
	version = NULL;

	if (time_lookups) {
		TIME_NOW(&start);
	}

	while (!done) {
		if (!quiet)
			printf("\n");
		if (fgets(s, sizeof(s), stdin) == NULL) {
			done = ISC_TRUE;
			continue;
		}
		len = strlen(s);
		if (len > 0U && s[len - 1] == '\n') {
			s[len - 1] = '\0';
			len--;
		}
		if (verbose && dbi != NULL) {
			if (dbi->wversion != NULL)
				printf("future version (%p)\n", dbi->wversion);
			for (i = 0; i < dbi->rcount; i++)
				if (dbi->rversions[i] != NULL)
					printf("open version %d (%p)\n", i,
					       dbi->rversions[i]);
		}
		dns_name_init(&name, offsets);
		if (strcmp(s, "!R") == 0) {
			DBI_CHECK(dbi);
			if (dbi->rcount == MAXVERSIONS) {
				printf("too many open versions\n");
				continue;
			}
			dns_db_currentversion(dbi->db,
					      &dbi->rversions[dbi->rcount]);
			printf("opened version %d\n", dbi->rcount);
			dbi->version = dbi->rversions[dbi->rcount];
			version = dbi->version;
			dbi->rcount++;
			continue;
		} else if (strcmp(s, "!W") == 0) {
			DBI_CHECK(dbi);
			if (dbi->wversion != NULL) {
				printf("using existing future version\n");
				dbi->version = dbi->wversion;
				version = dbi->version;
				continue;
			}
			result = dns_db_newversion(dbi->db, &dbi->wversion);
			if (result != ISC_R_SUCCESS)
				print_result("", result);
			else
				printf("newversion\n");
			dbi->version = dbi->wversion;
			version = dbi->version;
			continue;
		} else if (strcmp(s, "!C") == 0) {
			DBI_CHECK(dbi);
			addmode = ISC_FALSE;
			delmode = ISC_FALSE;
			if (dbi->version == NULL)
				continue;
			if (dbi->version == dbi->wversion) {
				printf("closing future version\n");
				dbi->wversion = NULL;
			} else {
				for (i = 0; i < dbi->rcount; i++) {
					if (dbi->version ==
					    dbi->rversions[i]) {
						dbi->rversions[i] = NULL;
					  printf("closing open version %d\n",
						 i);
						break;
					}
				}
			}
			dns_db_closeversion(dbi->db, &dbi->version, ISC_TRUE);
			version = NULL;
			continue;
		} else if (strcmp(s, "!X") == 0) {
			DBI_CHECK(dbi);
			addmode = ISC_FALSE;
			delmode = ISC_FALSE;
			if (dbi->version == NULL)
				continue;
			if (dbi->version == dbi->wversion) {
				printf("aborting future version\n");
				dbi->wversion = NULL;
			} else {
				for (i = 0; i < dbi->rcount; i++) {
					if (dbi->version ==
					    dbi->rversions[i]) {
						dbi->rversions[i] = NULL;
					  printf("closing open version %d\n",
						 i);
						break;
					}
				}
			}
			dns_db_closeversion(dbi->db, &dbi->version, ISC_FALSE);
			version = NULL;
			continue;
		} else if (strcmp(s, "!A") == 0) {
			DBI_CHECK(dbi);
			delmode = ISC_FALSE;
			if (addmode)
				addmode = ISC_FALSE;
			else
				addmode = ISC_TRUE;
			printf("addmode = %s\n", addmode ? "TRUE" : "FALSE");
			continue;
		} else if (strcmp(s, "!D") == 0) {
			DBI_CHECK(dbi);
			addmode = ISC_FALSE;
			if (delmode)
				delmode = ISC_FALSE;
			else
				delmode = ISC_TRUE;
			printf("delmode = %s\n", delmode ? "TRUE" : "FALSE");
			continue;
		} else if (strcmp(s, "!H") == 0) {
			DBI_CHECK(dbi);
			if (holdmode)
				holdmode = ISC_FALSE;
			else
				holdmode = ISC_TRUE;
			printf("holdmode = %s\n", holdmode ? "TRUE" : "FALSE");
			continue;
		} else if (strcmp(s, "!HR") == 0) {
			DBI_CHECK(dbi);
			for (i = 0; i < dbi->hold_count; i++)
				dns_db_detachnode(dbi->db,
						  &dbi->hold_nodes[i]);
			dbi->hold_count = 0;
			holdmode = ISC_FALSE;
			printf("held nodes have been detached\n");
			continue;
		} else if (strcmp(s, "!VC") == 0) {
			DBI_CHECK(dbi);
			printf("switching to current version\n");
			dbi->version = NULL;
			version = NULL;
			continue;
		} else if (strstr(s, "!V") == s) {
			DBI_CHECK(dbi);
			v = atoi(&s[2]);
			if (v >= dbi->rcount || v < 0) {
				printf("unknown open version %d\n", v);
				continue;
			}
			if (dbi->rversions[v] == NULL) {
				printf("version %d is not open\n", v);
				continue;
			}
			printf("switching to open version %d\n", v);
			dbi->version = dbi->rversions[v];
			version = dbi->version;
			continue;
		} else if (strstr(s, "!TR") == s) {
			trust = (unsigned int)atoi(&s[3]);
			printf("trust level is now %u\n", (unsigned int)trust);
			continue;
		} else if (strstr(s, "!T") == s) {
			type = (unsigned int)atoi(&s[2]);
			printf("now searching for type %u\n", type);
			continue;
		} else if (strcmp(s, "!G") == 0) {
			if ((options & DNS_DBFIND_GLUEOK) != 0)
				options &= ~DNS_DBFIND_GLUEOK;
			else
				options |= DNS_DBFIND_GLUEOK;
			printf("glue ok = %s\n",
			       ((options & DNS_DBFIND_GLUEOK) != 0) ?
			       "TRUE" : "FALSE");
			continue;
		} else if (strcmp(s, "!GV") == 0) {
			if ((options & DNS_DBFIND_VALIDATEGLUE) != 0)
				options &= ~DNS_DBFIND_VALIDATEGLUE;
			else
				options |= DNS_DBFIND_VALIDATEGLUE;
			printf("validate glue = %s\n",
			       ((options & DNS_DBFIND_VALIDATEGLUE) != 0) ?
			       "TRUE" : "FALSE");
			continue;
		} else if (strcmp(s, "!WC") == 0) {
			if ((options & DNS_DBFIND_NOWILD) != 0)
				options &= ~DNS_DBFIND_NOWILD;
			else
				options |= DNS_DBFIND_NOWILD;
			printf("wildcard matching = %s\n",
			       ((options & DNS_DBFIND_NOWILD) == 0) ?
			       "TRUE" : "FALSE");
			continue;
		} else if (strstr(s, "!LS ") == s) {
			DBI_CHECK(dbi);
			list(dbi, &s[4]);
			continue;
		} else if (strcmp(s, "!LS") == 0) {
			DBI_CHECK(dbi);
			list(dbi, NULL);
			continue;
		} else if (strstr(s, "!DU ") == s) {
			DBI_CHECK(dbi);
			result = dns_db_dump(dbi->db, dbi->version, s+4);
			if (result != ISC_R_SUCCESS) {
				printf("\n");
				print_result("", result);
			}
			continue;
		} else if (strcmp(s, "!PN") == 0) {
			if (printnode)
				printnode = ISC_FALSE;
			else
				printnode = ISC_TRUE;
			printf("printnode = %s\n",
			       printnode ? "TRUE" : "FALSE");
			continue;
		} else if (strstr(s, "!P") == s) {
			DBI_CHECK(dbi);
			v = atoi(&s[2]);
			dbi->pause_every = v;
			continue;
		} else if (strcmp(s, "!+") == 0) {
			DBI_CHECK(dbi);
			dbi->ascending = ISC_TRUE;
			continue;
		} else if (strcmp(s, "!-") == 0) {
			DBI_CHECK(dbi);
			dbi->ascending = ISC_FALSE;
			continue;
		} else if (strcmp(s, "!DB") == 0) {
			dbi = NULL;
			origin = dns_rootname;
			version = NULL;
			printf("now searching all databases\n");
			continue;
		} else if (strncmp(s, "!DB ", 4) == 0) {
			dbi = select_db(s+4);
			if (dbi != NULL) {
				db = dbi->db;
				origin = dns_db_origin(dbi->db);
				version = dbi->version;
				addmode = ISC_FALSE;
				delmode = ISC_FALSE;
				holdmode = ISC_FALSE;
			} else {
				db = NULL;
				version = NULL;
				origin = dns_rootname;
				printf("database not found; "
				       "now searching all databases\n");
			}
			continue;
		} else if (strcmp(s, "!ZC") == 0) {
			if (find_zonecut)
				find_zonecut = ISC_FALSE;
			else
				find_zonecut = ISC_TRUE;
			printf("find_zonecut = %s\n",
			       find_zonecut ? "TRUE" : "FALSE");
			continue;
		} else if (strcmp(s, "!NZ") == 0) {
			if (noexact_zonecut)
				noexact_zonecut = ISC_FALSE;
			else
				noexact_zonecut = ISC_TRUE;
			printf("noexact_zonecut = %s\n",
			       noexact_zonecut ? "TRUE" : "FALSE");
			continue;
		}

		isc_buffer_init(&source, s, len);
		isc_buffer_add(&source, len);
		isc_buffer_init(&target, b, sizeof(b));
		result = dns_name_fromtext(&name, &source, origin, 0, &target);
		if (result != ISC_R_SUCCESS) {
			print_result("bad name: ", result);
			continue;
		}

		if (dbi == NULL) {
			zcoptions = 0;
			if (noexact_zonecut)
				zcoptions |= DNS_DBTABLEFIND_NOEXACT;
			db = NULL;
			result = dns_dbtable_find(dbtable, &name, zcoptions,
						  &db);
			if (result != ISC_R_SUCCESS &&
			    result != DNS_R_PARTIALMATCH) {
				if (!quiet) {
					printf("\n");
					print_result("", result);
				}
				continue;
			}
			isc_buffer_init(&tb1, t1, sizeof(t1));
			result = dns_name_totext(dns_db_origin(db), ISC_FALSE,
						 &tb1);
			if (result != ISC_R_SUCCESS) {
				printf("\n");
				print_result("", result);
				dns_db_detach(&db);
				continue;
			}
			isc_buffer_usedregion(&tb1, &r1);
			printf("\ndatabase = %.*s (%s)\n",
			       (int)r1.length, r1.base,
			       (dns_db_iszone(db)) ? "zone" : "cache");
		}
		node = NULL;
		dns_rdataset_init(&rdataset);
		dns_rdataset_init(&sigrdataset);

		if (find_zonecut && dns_db_iscache(db)) {
			zcoptions = options;
			if (noexact_zonecut)
				zcoptions |= DNS_DBFIND_NOEXACT;
			result = dns_db_findzonecut(db, &name, zcoptions,
						    0, &node, fname,
						    &rdataset, &sigrdataset);
		} else {
			result = dns_db_find(db, &name, version, type,
					     options, 0, &node, fname,
					     &rdataset, &sigrdataset);
		}

		if (!quiet) {
			if (dbi != NULL)
				printf("\n");
			print_result("", result);
		}

		found_as = ISC_FALSE;
		switch (result) {
		case ISC_R_SUCCESS:
		case DNS_R_GLUE:
		case DNS_R_CNAME:
		case DNS_R_ZONECUT:
			break;
		case DNS_R_DNAME:
		case DNS_R_DELEGATION:
			found_as = ISC_TRUE;
			break;
		case DNS_R_NXRRSET:
			if (dns_rdataset_isassociated(&rdataset))
				break;
			if (dbi != NULL) {
				if (holdmode) {
					RUNTIME_CHECK(dbi->hold_count <
						      MAXHOLD);
					dbi->hold_nodes[dbi->hold_count++] =
						node;
					node = NULL;
				} else
					dns_db_detachnode(db, &node);
			} else {
				dns_db_detachnode(db, &node);
				dns_db_detach(&db);
			}
			continue;
		case DNS_R_NXDOMAIN:
			if (dns_rdataset_isassociated(&rdataset))
				break;
			/* FALLTHROUGH */
		default:
			if (dbi == NULL)
				dns_db_detach(&db);
			if (quiet)
				print_result("", result);
			continue;
		}
		if (found_as && !quiet) {
			isc_buffer_init(&tb1, t1, sizeof(t1));
			isc_buffer_init(&tb2, t2, sizeof(t2));
			result = dns_name_totext(&name, ISC_FALSE, &tb1);
			if (result != ISC_R_SUCCESS) {
				print_result("", result);
				dns_db_detachnode(db, &node);
				if (dbi == NULL)
					dns_db_detach(&db);
				continue;
			}
			result = dns_name_totext(fname, ISC_FALSE, &tb2);
			if (result != ISC_R_SUCCESS) {
				print_result("", result);
				dns_db_detachnode(db, &node);
				if (dbi == NULL)
					dns_db_detach(&db);
				continue;
			}
			isc_buffer_usedregion(&tb1, &r1);
			isc_buffer_usedregion(&tb2, &r2);
			printf("found %.*s as %.*s\n",
			       (int)r1.length, r1.base,
			       (int)r2.length, r2.base);
		}

		if (printnode)
			dns_db_printnode(db, node, stdout);

		if (!found_as && type == dns_rdatatype_any) {
			rdsiter = NULL;
			result = dns_db_allrdatasets(db, node, version, 0,
						     &rdsiter);
			if (result == ISC_R_SUCCESS) {
				if (!quiet)
					print_rdatasets(fname, rdsiter);
				dns_rdatasetiter_destroy(&rdsiter);
			} else
				print_result("", result);
		} else {
			if (!quiet)
				print_rdataset(fname, &rdataset);
			if (dns_rdataset_isassociated(&sigrdataset)) {
				if (!quiet)
					print_rdataset(fname, &sigrdataset);
				dns_rdataset_disassociate(&sigrdataset);
			}
			if (dbi != NULL && addmode && !found_as) {
				rdataset.ttl++;
				rdataset.trust = trust;
				if (dns_db_iszone(db))
					addopts = DNS_DBADD_MERGE;
				else
					addopts = 0;
				result = dns_db_addrdataset(db, node, version,
							    0, &rdataset,
							    addopts, NULL);
				if (result != ISC_R_SUCCESS)
					print_result("", result);
				if (printnode)
					dns_db_printnode(db, node, stdout);
			} else if (dbi != NULL && delmode && !found_as) {
				result = dns_db_deleterdataset(db, node,
							       version, type,
							       0);
				if (result != ISC_R_SUCCESS)
					print_result("", result);
				if (printnode)
					dns_db_printnode(db, node, stdout);
			}
			dns_rdataset_disassociate(&rdataset);
		}

		if (dbi != NULL) {
			if (holdmode) {
				RUNTIME_CHECK(dbi->hold_count < MAXHOLD);
				dbi->hold_nodes[dbi->hold_count++] = node;
				node = NULL;
			} else
				dns_db_detachnode(db, &node);
		} else {
			dns_db_detachnode(db, &node);
			dns_db_detach(&db);
		}
	}

	if (time_lookups) {
		isc_uint64_t usec;

		TIME_NOW(&finish);

		usec = isc_time_microdiff(&finish, &start);

		printf("elapsed time: %lu.%06lu seconds\n",
		       (unsigned long)(usec / 1000000),
		       (unsigned long)(usec % 1000000));
	}

	unload_all();

	dns_dbtable_detach(&dbtable);

	if (lctx != NULL)
		isc_log_destroy(&lctx);

	if (!quiet)
		isc_mem_stats(mctx, stdout);

	return (0);
}
Ejemplo n.º 13
0
static void
list(dbinfo *dbi, char *seektext) {
	dns_fixedname_t fname;
	dns_name_t *name;
	dns_dbnode_t *node;
	dns_rdatasetiter_t *rdsiter;
	isc_result_t result;
	int i;
	size_t len;
	dns_fixedname_t fseekname;
	dns_name_t *seekname;
	isc_buffer_t source;

	dns_fixedname_init(&fname);
	name = dns_fixedname_name(&fname);

	if (dbi->dbiterator == NULL) {
		INSIST(dbi->iversion == NULL);
		if (dns_db_iszone(dbi->db)) {
			if (dbi->version != NULL)
				dns_db_attachversion(dbi->db, dbi->version,
						     &dbi->iversion);
			else
				dns_db_currentversion(dbi->db, &dbi->iversion);
		}

		result = dns_db_createiterator(dbi->db, 0, &dbi->dbiterator);
		if (result == ISC_R_SUCCESS) {
			if (seektext != NULL) {
				len = strlen(seektext);
				isc_buffer_init(&source, seektext, len);
				isc_buffer_add(&source, len);
				dns_fixedname_init(&fseekname);
				seekname = dns_fixedname_name(&fseekname);
				result = dns_name_fromtext(seekname, &source,
							   dns_db_origin(
								 dbi->db),
							   0, NULL);
				if (result == ISC_R_SUCCESS)
					result = dns_dbiterator_seek(
							     dbi->dbiterator,
							     seekname);
			} else if (dbi->ascending)
				result = dns_dbiterator_first(dbi->dbiterator);
			else
				result = dns_dbiterator_last(dbi->dbiterator);
		}
	} else
		result = ISC_R_SUCCESS;

	node = NULL;
	rdsiter = NULL;
	i = 0;
	while (result == ISC_R_SUCCESS) {
		result = dns_dbiterator_current(dbi->dbiterator, &node, name);
		if (result != ISC_R_SUCCESS && result != DNS_R_NEWORIGIN)
			break;
		result = dns_db_allrdatasets(dbi->db, node, dbi->iversion, 0,
					     &rdsiter);
		if (result != ISC_R_SUCCESS) {
			dns_db_detachnode(dbi->db, &node);
			break;
		}
		print_rdatasets(name, rdsiter);
		dns_rdatasetiter_destroy(&rdsiter);
		dns_db_detachnode(dbi->db, &node);
		if (dbi->ascending)
			result = dns_dbiterator_next(dbi->dbiterator);
		else
			result = dns_dbiterator_prev(dbi->dbiterator);
		i++;
		if (result == ISC_R_SUCCESS && i == dbi->pause_every) {
			printf("[more...]\n");
			result = dns_dbiterator_pause(dbi->dbiterator);
			if (result == ISC_R_SUCCESS)
				return;
		}
	}
	if (result != ISC_R_NOMORE)
		print_result("", result);

	dns_dbiterator_destroy(&dbi->dbiterator);
	if (dbi->iversion != NULL)
		dns_db_closeversion(dbi->db, &dbi->iversion, ISC_FALSE);
}
Ejemplo n.º 14
0
isc_result_t
dns_nsec_buildrdata(dns_db_t *db, dns_dbversion_t *version,
		    dns_dbnode_t *node, dns_name_t *target,
		    unsigned char *buffer, dns_rdata_t *rdata)
{
	isc_result_t result;
	dns_rdataset_t rdataset;
	isc_region_t r;
	unsigned int i;

	unsigned char *nsec_bits, *bm;
	unsigned int max_type;
	dns_rdatasetiter_t *rdsiter;

	memset(buffer, 0, DNS_NSEC_BUFFERSIZE);
	dns_name_toregion(target, &r);
	memcpy(buffer, r.base, r.length);
	r.base = buffer;
	/*
	 * Use the end of the space for a raw bitmap leaving enough
	 * space for the window identifiers and length octets.
	 */
	bm = r.base + r.length + 512;
	nsec_bits = r.base + r.length;
	dns_nsec_setbit(bm, dns_rdatatype_rrsig, 1);
	dns_nsec_setbit(bm, dns_rdatatype_nsec, 1);
	max_type = dns_rdatatype_nsec;
	dns_rdataset_init(&rdataset);
	rdsiter = NULL;
	result = dns_db_allrdatasets(db, node, version, 0, &rdsiter);
	if (result != ISC_R_SUCCESS)
		return (result);
	for (result = dns_rdatasetiter_first(rdsiter);
	     result == ISC_R_SUCCESS;
	     result = dns_rdatasetiter_next(rdsiter))
	{
		dns_rdatasetiter_current(rdsiter, &rdataset);
		if (rdataset.type != dns_rdatatype_nsec &&
		    rdataset.type != dns_rdatatype_nsec3 &&
		    rdataset.type != dns_rdatatype_rrsig) {
			if (rdataset.type > max_type)
				max_type = rdataset.type;
			dns_nsec_setbit(bm, rdataset.type, 1);
		}
		dns_rdataset_disassociate(&rdataset);
	}

	/*
	 * At zone cuts, deny the existence of glue in the parent zone.
	 */
	if (dns_nsec_isset(bm, dns_rdatatype_ns) &&
	    ! dns_nsec_isset(bm, dns_rdatatype_soa)) {
		for (i = 0; i <= max_type; i++) {
			if (dns_nsec_isset(bm, i) &&
			    ! dns_rdatatype_iszonecutauth((dns_rdatatype_t)i))
				dns_nsec_setbit(bm, i, 0);
		}
	}

	dns_rdatasetiter_destroy(&rdsiter);
	if (result != ISC_R_NOMORE)
		return (result);

	nsec_bits += dns_nsec_compressbitmap(nsec_bits, bm, max_type);

	r.length = nsec_bits - r.base;
	INSIST(r.length <= DNS_NSEC_BUFFERSIZE);
	dns_rdata_fromregion(rdata,
			     dns_db_class(db),
			     dns_rdatatype_nsec,
			     &r);

	return (ISC_R_SUCCESS);
}
Ejemplo n.º 15
0
/*% scan the zone for oversize TTLs */
static isc_result_t
check_ttls(dns_zone_t *zone, dns_ttl_t maxttl) {
	isc_result_t result;
	dns_db_t *db = NULL;
	dns_dbversion_t *version = NULL;
	dns_dbnode_t *node = NULL;
	dns_dbiterator_t *dbiter = NULL;
	dns_rdatasetiter_t *rdsiter = NULL;
	dns_rdataset_t rdataset;
	dns_fixedname_t fname;
	dns_name_t *name;
	dns_fixedname_init(&fname);
	name = dns_fixedname_name(&fname);
	dns_rdataset_init(&rdataset);

	CHECK(dns_zone_getdb(zone, &db));
	INSIST(db != NULL);

	CHECK(dns_db_newversion(db, &version));
	CHECK(dns_db_createiterator(db, 0, &dbiter));

	for (result = dns_dbiterator_first(dbiter);
	     result == ISC_R_SUCCESS;
	     result = dns_dbiterator_next(dbiter)) {
		result = dns_dbiterator_current(dbiter, &node, name);
		if (result == DNS_R_NEWORIGIN)
			result = ISC_R_SUCCESS;
		CHECK(result);

		CHECK(dns_db_allrdatasets(db, node, version, 0, &rdsiter));
		for (result = dns_rdatasetiter_first(rdsiter);
		     result == ISC_R_SUCCESS;
		     result = dns_rdatasetiter_next(rdsiter)) {
			dns_rdatasetiter_current(rdsiter, &rdataset);
			if (rdataset.ttl > maxttl) {
				char nbuf[DNS_NAME_FORMATSIZE];
				char tbuf[255];
				isc_buffer_t b;
				isc_region_t r;

				dns_name_format(name, nbuf, sizeof(nbuf));
				isc_buffer_init(&b, tbuf, sizeof(tbuf) - 1);
				CHECK(dns_rdatatype_totext(rdataset.type, &b));
				isc_buffer_usedregion(&b, &r);
				r.base[r.length] = 0;

				dns_zone_log(zone, ISC_LOG_ERROR,
					     "%s/%s TTL %d exceeds "
					     "maximum TTL %d",
					     nbuf, tbuf, rdataset.ttl, maxttl);
				dns_rdataset_disassociate(&rdataset);
				CHECK(ISC_R_RANGE);
			}
			dns_rdataset_disassociate(&rdataset);
		}
		if (result == ISC_R_NOMORE)
			result = ISC_R_SUCCESS;
		CHECK(result);

		dns_rdatasetiter_destroy(&rdsiter);
		dns_db_detachnode(db, &node);
	}

	if (result == ISC_R_NOMORE)
		result = ISC_R_SUCCESS;

 cleanup:
	if (node != NULL)
		dns_db_detachnode(db, &node);
	if (rdsiter != NULL)
		dns_rdatasetiter_destroy(&rdsiter);
	if (dbiter != NULL)
		dns_dbiterator_destroy(&dbiter);
	if (version != NULL)
		dns_db_closeversion(db, &version, ISC_FALSE);
	if (db != NULL)
		dns_db_detach(&db);

	return (result);
}
Ejemplo n.º 16
0
static isc_result_t
iterate_node(lwres_grbnresponse_t *grbn, dns_db_t *db, dns_dbnode_t *node,
	     isc_mem_t *mctx)
{
	int used = 0, count;
	int size = 8, oldsize = 0;
	unsigned char **rdatas = NULL, **oldrdatas = NULL, **newrdatas = NULL;
	lwres_uint16_t *lens = NULL, *oldlens = NULL, *newlens = NULL;
	dns_rdatasetiter_t *iter = NULL;
	dns_rdataset_t set;
	dns_ttl_t ttl = ISC_INT32_MAX;
	lwres_uint32_t flags = LWRDATA_VALIDATED;
	isc_result_t result = ISC_R_NOMEMORY;

	result = dns_db_allrdatasets(db, node, NULL, 0, &iter);
	if (result != ISC_R_SUCCESS)
		goto out;

	rdatas = isc_mem_get(mctx, size * sizeof(*rdatas));
	if (rdatas == NULL)
		goto out;
	lens = isc_mem_get(mctx, size * sizeof(*lens));
	if (lens == NULL)
		goto out;

	for (result = dns_rdatasetiter_first(iter);
	     result == ISC_R_SUCCESS;
	     result = dns_rdatasetiter_next(iter))
	{
		result = ISC_R_NOMEMORY;
		dns_rdataset_init(&set);
		dns_rdatasetiter_current(iter, &set);

		if (set.type != dns_rdatatype_rrsig) {
			dns_rdataset_disassociate(&set);
			continue;
		}

		count = dns_rdataset_count(&set);
		if (used + count > size) {
			/* copy & reallocate */
			oldsize = size;
			oldrdatas = rdatas;
			oldlens = lens;
			rdatas = NULL;
			lens = NULL;

			size *= 2;

			rdatas = isc_mem_get(mctx, size * sizeof(*rdatas));
			if (rdatas == NULL)
				goto out;
			lens = isc_mem_get(mctx, size * sizeof(*lens));
			if (lens == NULL)
				goto out;
			memmove(rdatas, oldrdatas, used * sizeof(*rdatas));
			memmove(lens, oldlens, used * sizeof(*lens));
			isc_mem_put(mctx, oldrdatas,
				    oldsize * sizeof(*oldrdatas));
			isc_mem_put(mctx, oldlens, oldsize * sizeof(*oldlens));
			oldrdatas = NULL;
			oldlens = NULL;
		}
		if (set.ttl < ttl)
			ttl = set.ttl;
		if (set.trust != dns_trust_secure)
			flags &= (~LWRDATA_VALIDATED);
		result = fill_array(&used, &set, size, rdatas, lens);
		dns_rdataset_disassociate(&set);
		if (result != ISC_R_SUCCESS)
			goto out;
	}
	if (result == ISC_R_NOMORE)
		result = ISC_R_SUCCESS;
	if (result != ISC_R_SUCCESS)
		goto out;
	dns_rdatasetiter_destroy(&iter);

	/*
	 * If necessary, shrink and copy the arrays.
	 */
	if (size != used) {
		result = ISC_R_NOMEMORY;
		newrdatas = isc_mem_get(mctx, used * sizeof(*rdatas));
		if (newrdatas == NULL)
			goto out;
		newlens = isc_mem_get(mctx, used * sizeof(*lens));
		if (newlens == NULL)
			goto out;
		memmove(newrdatas, rdatas, used * sizeof(*rdatas));
		memmove(newlens, lens, used * sizeof(*lens));
		isc_mem_put(mctx, rdatas, size * sizeof(*rdatas));
		isc_mem_put(mctx, lens, size * sizeof(*lens));
		grbn->rdatas = newrdatas;
		grbn->rdatalen = newlens;
	} else {
		grbn->rdatas = rdatas;
		grbn->rdatalen = lens;
	}
	grbn->nrdatas = used;
	grbn->ttl = ttl;
	grbn->flags = flags;
	return (ISC_R_SUCCESS);

 out:
	dns_rdatasetiter_destroy(&iter);
	if (rdatas != NULL)
		isc_mem_put(mctx, rdatas, size * sizeof(*rdatas));
	if (lens != NULL)
		isc_mem_put(mctx, lens, size * sizeof(*lens));
	if (oldrdatas != NULL)
		isc_mem_put(mctx, oldrdatas, oldsize * sizeof(*oldrdatas));
	if (oldlens != NULL)
		isc_mem_put(mctx, oldlens, oldsize * sizeof(*oldlens));
	if (newrdatas != NULL)
		isc_mem_put(mctx, newrdatas, used * sizeof(*oldrdatas));
	return (result);
}
Ejemplo n.º 17
0
isc_result_t
dns_nsec_buildrdata(dns_db_t *db, dns_dbversion_t *version,
		    dns_dbnode_t *node, dns_name_t *target,
		    unsigned char *buffer, dns_rdata_t *rdata)
{
	isc_result_t result;
	dns_rdataset_t rdataset;
	isc_region_t r;
	unsigned int i, window;
	int octet;

	unsigned char *nsec_bits, *bm;
	unsigned int max_type;
	dns_rdatasetiter_t *rdsiter;

	memset(buffer, 0, DNS_NSEC_BUFFERSIZE);
	dns_name_toregion(target, &r);
	memcpy(buffer, r.base, r.length);
	r.base = buffer;
	/*
	 * Use the end of the space for a raw bitmap leaving enough
	 * space for the window identifiers and length octets.
	 */
	bm = r.base + r.length + 512;
	nsec_bits = r.base + r.length;
	set_bit(bm, dns_rdatatype_rrsig, 1);
	set_bit(bm, dns_rdatatype_nsec, 1);
	max_type = dns_rdatatype_nsec;
	dns_rdataset_init(&rdataset);
	rdsiter = NULL;
	result = dns_db_allrdatasets(db, node, version, 0, &rdsiter);
	if (result != ISC_R_SUCCESS)
		return (result);
	for (result = dns_rdatasetiter_first(rdsiter);
	     result == ISC_R_SUCCESS;
	     result = dns_rdatasetiter_next(rdsiter))
	{
		dns_rdatasetiter_current(rdsiter, &rdataset);
		if (rdataset.type != dns_rdatatype_nsec &&
		    rdataset.type != dns_rdatatype_nsec3 &&
		    rdataset.type != dns_rdatatype_rrsig) {
			if (rdataset.type > max_type)
				max_type = rdataset.type;
			set_bit(bm, rdataset.type, 1);
		}
		dns_rdataset_disassociate(&rdataset);
	}

	/*
	 * At zone cuts, deny the existence of glue in the parent zone.
	 */
	if (bit_isset(bm, dns_rdatatype_ns) &&
	    ! bit_isset(bm, dns_rdatatype_soa)) {
		for (i = 0; i <= max_type; i++) {
			if (bit_isset(bm, i) &&
			    ! dns_rdatatype_iszonecutauth((dns_rdatatype_t)i))
				set_bit(bm, i, 0);
		}
	}

	dns_rdatasetiter_destroy(&rdsiter);
	if (result != ISC_R_NOMORE)
		return (result);

	for (window = 0; window < 256; window++) {
		if (window * 256 > max_type)
			break;
		for (octet = 31; octet >= 0; octet--)
			if (bm[window * 32 + octet] != 0)
				break;
		if (octet < 0)
			continue;
		nsec_bits[0] = window;
		nsec_bits[1] = octet + 1;
		/*
		 * Note: potential overlapping move.
		 */
		memmove(&nsec_bits[2], &bm[window * 32], octet + 1);
		nsec_bits += 3 + octet;
	}
	r.length = nsec_bits - r.base;
	INSIST(r.length <= DNS_NSEC_BUFFERSIZE);
	dns_rdata_fromregion(rdata,
			     dns_db_class(db),
			     dns_rdatatype_nsec,
			     &r);

	return (ISC_R_SUCCESS);
}
Ejemplo n.º 18
0
isc_result_t
dns_nsec3_buildrdata(dns_db_t *db, dns_dbversion_t *version,
		     dns_dbnode_t *node, unsigned int hashalg,
		     unsigned int flags, unsigned int iterations,
		     const unsigned char *salt, size_t salt_length,
		     const unsigned char *nexthash, size_t hash_length,
		     unsigned char *buffer, dns_rdata_t *rdata)
{
	isc_result_t result;
	dns_rdataset_t rdataset;
	isc_region_t r;
	unsigned int i, window;
	int octet;
	isc_boolean_t found;
	isc_boolean_t found_ns;
	isc_boolean_t need_rrsig;

	unsigned char *nsec_bits, *bm;
	unsigned int max_type;
	dns_rdatasetiter_t *rdsiter;
	unsigned char *p;

	REQUIRE(salt_length < 256U);
	REQUIRE(hash_length < 256U);
	REQUIRE(flags <= 0xffU);
	REQUIRE(hashalg <= 0xffU);
	REQUIRE(iterations <= 0xffffU);

	switch (hashalg) {
	case dns_hash_sha1:
		REQUIRE(hash_length == ISC_SHA1_DIGESTLENGTH);
		break;
	}

	memset(buffer, 0, DNS_NSEC3_BUFFERSIZE);

	p = buffer;

	*p++ = hashalg;
	*p++ = flags;

	*p++ = iterations >> 8;
	*p++ = iterations;

	*p++ = salt_length;
	memcpy(p, salt, salt_length);
	p += salt_length;

	*p++ = hash_length;
	memcpy(p, nexthash, hash_length);
	p += hash_length;

	r.length = p - buffer;
	r.base = buffer;

	/*
	 * Use the end of the space for a raw bitmap leaving enough
	 * space for the window identifiers and length octets.
	 */
	bm = r.base + r.length + 512;
	nsec_bits = r.base + r.length;
	max_type = 0;
	if (node == NULL)
		goto collapse_bitmap;
	dns_rdataset_init(&rdataset);
	rdsiter = NULL;
	result = dns_db_allrdatasets(db, node, version, 0, &rdsiter);
	if (result != ISC_R_SUCCESS)
		return (result);
	found = found_ns = need_rrsig = ISC_FALSE;
	for (result = dns_rdatasetiter_first(rdsiter);
	     result == ISC_R_SUCCESS;
	     result = dns_rdatasetiter_next(rdsiter))
	{
		dns_rdatasetiter_current(rdsiter, &rdataset);
		if (rdataset.type != dns_rdatatype_nsec &&
		    rdataset.type != dns_rdatatype_nsec3 &&
		    rdataset.type != dns_rdatatype_rrsig) {
			if (rdataset.type > max_type)
				max_type = rdataset.type;
			set_bit(bm, rdataset.type, 1);
			/*
			 * Work out if we need to set the RRSIG bit for
			 * this node.  We set the RRSIG bit if either of
			 * the following conditions are met:
			 * 1) We have a SOA or DS then we need to set
			 *    the RRSIG bit as both always will be signed.
			 * 2) We set the RRSIG bit if we don't have
			 *    a NS record but do have other data.
			 */
			if (rdataset.type == dns_rdatatype_soa ||
			    rdataset.type == dns_rdatatype_ds)
				need_rrsig = ISC_TRUE;
			else if (rdataset.type == dns_rdatatype_ns)
				found_ns = ISC_TRUE;
			else
				found = ISC_TRUE;
		}
		dns_rdataset_disassociate(&rdataset);
	}
	if ((found && !found_ns) || need_rrsig) {
		if (dns_rdatatype_rrsig > max_type)
			max_type = dns_rdatatype_rrsig;
		set_bit(bm, dns_rdatatype_rrsig, 1);
	}

	/*
	 * At zone cuts, deny the existence of glue in the parent zone.
	 */
	if (bit_isset(bm, dns_rdatatype_ns) &&
	    ! bit_isset(bm, dns_rdatatype_soa)) {
		for (i = 0; i <= max_type; i++) {
			if (bit_isset(bm, i) &&
			    ! dns_rdatatype_iszonecutauth((dns_rdatatype_t)i))
				set_bit(bm, i, 0);
		}
	}

	dns_rdatasetiter_destroy(&rdsiter);
	if (result != ISC_R_NOMORE)
		return (result);

 collapse_bitmap:
	for (window = 0; window < 256; window++) {
		if (window * 256 > max_type)
			break;
		for (octet = 31; octet >= 0; octet--)
			if (bm[window * 32 + octet] != 0)
				break;
		if (octet < 0)
			continue;
		nsec_bits[0] = window;
		nsec_bits[1] = octet + 1;
		/*
		 * Note: potentially overlapping move.
		 */
		memmove(&nsec_bits[2], &bm[window * 32], octet + 1);
		nsec_bits += 3 + octet;
	}
	r.length = nsec_bits - r.base;
	INSIST(r.length <= DNS_NSEC3_BUFFERSIZE);
	dns_rdata_fromregion(rdata, dns_db_class(db), dns_rdatatype_nsec3, &r);

	return (ISC_R_SUCCESS);
}
Ejemplo n.º 19
0
int
main(int argc, char *argv[])
{
	isc_mem_t *mctx = NULL;
	isc_buffer_t b;
	int n;
	dns_fixedname_t origin, name;
	dns_db_t *db = NULL;
	dns_dbiterator_t *dbiter = NULL;
	isc_result_t res;
	dns_dbnode_t *node = NULL;
	dns_rdataset_t rdataset;
	dns_rdatasetiter_t *rdatasetiter = NULL;
	dns_rdata_t rdata;
	DB *bdb;

	if (argc != 4) usage(*argv);

	REQUIRE(isc_mem_create(0, 0, &mctx) == ISC_R_SUCCESS);

	n = strlen(argv[1]);
	isc_buffer_init(&b, argv[1], n);
	isc_buffer_add(&b, n);

	dns_fixedname_init(&origin);

	REQUIRE(dns_name_fromtext(dns_fixedname_name(&origin), &b, dns_rootname,
				  0, NULL) == ISC_R_SUCCESS);
	REQUIRE(dns_db_create(mctx, "rbt", dns_fixedname_name(&origin),
			      dns_dbtype_zone, dns_rdataclass_in, 0, NULL,
			      &db) == ISC_R_SUCCESS);

	REQUIRE(dns_db_load(db, argv[2]) == ISC_R_SUCCESS);

	REQUIRE(dns_db_createiterator(db, 0, &dbiter) == ISC_R_SUCCESS);

	dns_rdataset_init(&rdataset);
	dns_rdata_init(&rdata);
	dns_fixedname_init(&name);
	bdb = bdb_init(argv[3]);

	for (res = dns_dbiterator_first(dbiter); res == ISC_R_SUCCESS;
	    res = dns_dbiterator_next(dbiter)) {
		dns_dbiterator_current(dbiter, &node, dns_fixedname_name(&name));
		REQUIRE(dns_db_allrdatasets(db, node, NULL, 0, &rdatasetiter)
		    == ISC_R_SUCCESS);

		for (res = dns_rdatasetiter_first(rdatasetiter);
		    res == ISC_R_SUCCESS;
		    res = dns_rdatasetiter_next(rdatasetiter)) {
			dns_rdatasetiter_current(rdatasetiter, &rdataset);

			res = dns_rdataset_first(&rdataset);
			while (res == ISC_R_SUCCESS) {
				dns_rdataset_current(&rdataset, &rdata);
				REQUIRE(bdb_putrdata(bdb,
						     dns_fixedname_name(&name),
						     rdataset.ttl, &rdata)
					== ISC_R_SUCCESS);

				dns_rdata_reset(&rdata);
				res = dns_rdataset_next(&rdataset);
			}

			dns_rdataset_disassociate(&rdataset);
		}
		dns_rdatasetiter_destroy(&rdatasetiter);
		dns_db_detachnode(db, &node);
	}
	dns_dbiterator_destroy(&dbiter);

	REQUIRE(bdb_destroy(bdb) == ISC_R_SUCCESS);

	return 0;
}
Ejemplo n.º 20
0
int
main(int argc, char *argv[])
{
    char *sql;
    int res;
    char *errmsg = NULL;
    char *porigin, *zonefile;
    dns_fixedname_t forigin, fname;
    dns_name_t *origin, *name;
    dns_db_t *db = NULL;
    dns_dbiterator_t *dbiter;
    dns_dbnode_t *node;
    dns_rdatasetiter_t *rdsiter;
    dns_rdataset_t rdataset;
    dns_rdata_t rdata = DNS_RDATA_INIT;
    isc_mem_t *mctx = NULL;
    isc_entropy_t *ectx = NULL;
    isc_buffer_t b;
    isc_result_t result;

    if (argc != 5) {
	printf("usage: %s <zone> <zonefile> <dbfile> <dbtable>\n", argv[0]);
	exit(1);
    }
    
    porigin  = argv[1];
    zonefile = argv[2];

    dbi.filename = argv[3];
    dbi.table    = argv[4];
    
    dns_result_register();
    
    result = isc_mem_create(0, 0, &mctx);
    check_result(result, "isc_mem_create");
    result = isc_entropy_create(mctx, &ectx);
    check_result(result, "isc_entropy_create");
    result = isc_hash_create(mctx, ectx, DNS_NAME_MAXWIRE);
    check_result(result, "isc_hash_create");
    
    isc_buffer_init(&b, porigin, strlen(porigin));
    isc_buffer_add(&b, strlen(porigin));
    dns_fixedname_init(&forigin);
    origin = dns_fixedname_name(&forigin);
    result = dns_name_fromtext(origin, &b, dns_rootname, 0, NULL);
    check_result(result, "dns_name_fromtext");
    
    db = NULL;
    result = dns_db_create(mctx, "rbt", origin, dns_dbtype_zone,
			   dns_rdataclass_in, 0, NULL, &db);
    check_result(result, "dns_db_create");
    
    result = dns_db_load(db, zonefile);
    if (result == DNS_R_SEENINCLUDE)
	result = ISC_R_SUCCESS;
    check_result(result, "dns_db_load");

    printf("Connecting to '%s'\n", dbi.filename);
    
    if ((result = db_connect(&dbi)) != ISC_R_SUCCESS) {
	fprintf(stderr, "Connection to database '%s' failed\n",
		dbi.filename);
	closeandexit(1);
    }
    
    sql = sqlite3_mprintf("DROP TABLE %q ", dbi.table);
    printf("%s\n", sql);
    res = sqlite3_exec(dbi.db, sql, NULL, NULL, &errmsg);
    sqlite3_free(sql);
#if 0
    if (res != SQLITE_OK) {
	fprintf(stderr, "DROP TABLE %s failed: %s\n",
		dbi.table, errmsg);
    }
#endif

#if 0    
    sql = sqlite3_mprintf(sql, "BEGIN TRANSACTION");
    printf("%s\n", sql);
    res = sqlite3_exec(dbi.db, sql, NULL, NULL, &errmsg);
    sqlite3_free(sql);
    if (res != SQLITE_OK) {
	fprintf(stderr, "BEGIN TRANSACTION failed: %s\n", errmsg);
	closeandexit(1);
    }
#endif
    
    sql = sqlite3_mprintf(
	"CREATE TABLE %q "
	"(NAME TEXT, TTL INTEGER, RDTYPE TEXT, RDATA TEXT) ",
	dbi.table);
    printf("%s\n", sql);
    res = sqlite3_exec(dbi.db, sql, NULL, NULL, &errmsg);
    sqlite3_free(sql);
    if (res != SQLITE_OK) {
	fprintf(stderr, "CREATE TABLE %s failed: %s\n",
		dbi.table, errmsg);
	closeandexit(1);
    }
    
    dbiter = NULL;
    result = dns_db_createiterator(db, 0, &dbiter);
    check_result(result, "dns_db_createiterator()");
    
    result = dns_dbiterator_first(dbiter);
    check_result(result, "dns_dbiterator_first");
    
    dns_fixedname_init(&fname);
    name = dns_fixedname_name(&fname);
    dns_rdataset_init(&rdataset);
    dns_rdata_init(&rdata);
    
    while (result == ISC_R_SUCCESS) {
	node = NULL;
	result = dns_dbiterator_current(dbiter, &node, name);
	if (result == ISC_R_NOMORE)
	    break;
	check_result(result, "dns_dbiterator_current");
	
	rdsiter = NULL;
	result = dns_db_allrdatasets(db, node, NULL, 0, &rdsiter);
	check_result(result, "dns_db_allrdatasets");

	result = dns_rdatasetiter_first(rdsiter);

	while (result == ISC_R_SUCCESS) {
	    dns_rdatasetiter_current(rdsiter, &rdataset);
	    result = dns_rdataset_first(&rdataset);
	    check_result(result, "dns_rdataset_first");
	    while (result == ISC_R_SUCCESS) {
		dns_rdataset_current(&rdataset, &rdata);
		addrdata(name, rdataset.ttl, &rdata);
		dns_rdata_reset(&rdata);
		result = dns_rdataset_next(&rdataset);
	    }
	    dns_rdataset_disassociate(&rdataset);
	    result = dns_rdatasetiter_next(rdsiter);
	}
	dns_rdatasetiter_destroy(&rdsiter);
	dns_db_detachnode(db, &node);
	result = dns_dbiterator_next(dbiter);
    }

#if 0
    sql = sqlite3_mprintf(sql, "COMMIT TRANSACTION ");
    printf("%s\n", sql);
    res = sqlite3_exec(dbi.db, sql, NULL, NULL, &errmsg);
    sqlite3_free(sql);
    if (res != SQLITE_OK) {
	fprintf(stderr, "COMMIT TRANSACTION failed: %s\n", errmsg);
	closeandexit(1);
    }
#endif
    
    dns_dbiterator_destroy(&dbiter);
    dns_db_detach(&db);
    isc_hash_destroy();
    isc_entropy_detach(&ectx);
    isc_mem_destroy(&mctx);

    closeandexit(0);

    exit(0);
}
Ejemplo n.º 21
0
int
main (int *argc, char **argv)
{
  isc_mem_t *mctx = NULL;
  isc_entropy_t *ectx = NULL;
  isc_result_t result;
  char *basedn;
  ldap_info *tmp;
  LDAPMod *base_attrs[2];
  LDAPMod base;
  isc_buffer_t buff;
  char *zonefile;
  char fullbasedn[1024];
  char *ctmp;
  dns_fixedname_t fixedzone, fixedname;
  dns_rdataset_t rdataset;
  char **dc_list;
  dns_rdata_t rdata = DNS_RDATA_INIT;
  dns_rdatasetiter_t *riter;
  dns_name_t *zone, *name;
  dns_db_t *db = NULL;
  dns_dbiterator_t *dbit = NULL;
  dns_dbnode_t *node;
  extern char *optarg;
  extern int optind, opterr, optopt;
  int create_base = 0;
  int topt;

  if ((int) argc < 2)
    {
      usage ();
      exit (-1);
    }

  while ((topt = getopt ((int) argc, argv, "D:w:b:z:f:h:?dcv")) != -1)
    {
      switch (topt)
	{
	case 'v':
		printf("%s\n", VERSION);
		exit(0);
	case 'c':
	  create_base++;
	  break;
	case 'd':
	  debug++;
	  break;
	case 'D':
	  binddn = strdup (optarg);
	  break;
	case 'w':
	  bindpw = strdup (optarg);
	  break;
	case 'b':
	  ldapbase = strdup (optarg);
	  break;
	case 'z':
	  argzone = strdup (optarg);
	  // We wipe argzone all to hell when we parse it for the DN */
	  gbl_zone = strdup(argzone);
	  break;
	case 'f':
	  zonefile = strdup (optarg);
	  break;
	case 'h':
	  ldapsystem = strdup (optarg);
	  break;
	case '?':
	default:
	  usage ();
	  exit (0);
	}
    }

  if ((argzone == NULL) || (zonefile == NULL))
    {
      usage ();
      exit (-1);
    }

  if (debug)
    printf ("Initializing ISC Routines, parsing zone file\n");

  result = isc_mem_create (0, 0, &mctx);
  isc_result_check (result, "isc_mem_create");

  result = isc_entropy_create(mctx, &ectx);
  isc_result_check (result, "isc_entropy_create");

  result = isc_hash_create(mctx, ectx, DNS_NAME_MAXWIRE);
  isc_result_check (result, "isc_hash_create");

  isc_buffer_init (&buff, argzone, strlen (argzone));
  isc_buffer_add (&buff, strlen (argzone));
  dns_fixedname_init (&fixedzone);
  zone = dns_fixedname_name (&fixedzone);
  result = dns_name_fromtext (zone, &buff, dns_rootname, 0, NULL);
  isc_result_check (result, "dns_name_fromtext");

  result = dns_db_create (mctx, "rbt", zone, dns_dbtype_zone,
			  dns_rdataclass_in, 0, NULL, &db);
  isc_result_check (result, "dns_db_create");

  result = dns_db_load (db, zonefile);
  isc_result_check (result, "Check Zone Syntax: dns_db_load");

  result = dns_db_createiterator (db, 0, &dbit);
  isc_result_check (result, "dns_db_createiterator");

  result = dns_dbiterator_first (dbit);
  isc_result_check (result, "dns_dbiterator_first");

  dns_fixedname_init (&fixedname);
  name = dns_fixedname_name (&fixedname);
  dns_rdataset_init (&rdataset);
  dns_rdata_init (&rdata);

  while (result == ISC_R_SUCCESS)
    {
      node = NULL;
      result = dns_dbiterator_current (dbit, &node, name);

      if (result == ISC_R_NOMORE)
	break;

      isc_result_check (result, "dns_dbiterator_current");

      riter = NULL;
      result = dns_db_allrdatasets (db, node, NULL, 0, &riter);
      isc_result_check (result, "dns_db_allrdatasets");

      result = dns_rdatasetiter_first (riter);
      //isc_result_check(result, "dns_rdatasetiter_first");

      while (result == ISC_R_SUCCESS)
	{
	  dns_rdatasetiter_current (riter, &rdataset);
	  result = dns_rdataset_first (&rdataset);
	  isc_result_check (result, "dns_rdatasetiter_current");

	  while (result == ISC_R_SUCCESS)
	    {
	      dns_rdataset_current (&rdataset, &rdata);
	      generate_ldap (name, &rdata, rdataset.ttl);
	      dns_rdata_reset (&rdata);
	      result = dns_rdataset_next (&rdataset);
	    }
	  dns_rdataset_disassociate (&rdataset);
	  result = dns_rdatasetiter_next (riter);

	}
      dns_rdatasetiter_destroy (&riter);
      result = dns_dbiterator_next (dbit);

    }

  /* Initialize the LDAP Connection */
  if (debug)
    printf ("Initializing LDAP Connection to %s as %s\n", ldapsystem, binddn);

  init_ldap_conn ();

  if (create_base)
    {
      if (debug)
	printf ("Creating base zone DN %s\n", argzone);

      dc_list = hostname_to_dn_list (argzone, argzone, DNS_TOP);
      basedn = build_dn_from_dc_list (dc_list, 0, NO_SPEC);

      for (ctmp = &basedn[strlen (basedn)]; ctmp >= &basedn[0]; ctmp--)
	{
	  if ((*ctmp == ',') || (ctmp == &basedn[0]))
	    {
	      base.mod_op = LDAP_MOD_ADD;
	      base.mod_type = "objectClass";
	      base.mod_values = topObjectClasses;
	      base_attrs[0] = &base;
	      base_attrs[1] = NULL;

	      if (ldapbase)
		{
		  if (ctmp != &basedn[0])
		    sprintf (fullbasedn, "%s,%s", ctmp + 1, ldapbase);
		  else
		    sprintf (fullbasedn, "%s,%s", ctmp, ldapbase);

		}
	      else
		{
		  if (ctmp != &basedn[0])
		    sprintf (fullbasedn, "%s", ctmp + 1);
		  else
		    sprintf (fullbasedn, "%s", ctmp);
		}
	      result = ldap_add_s (conn, fullbasedn, base_attrs);
	      ldap_result_check ("intial ldap_add_s", fullbasedn, result);
	    }

	}
    }
  else
    {
      if (debug)
	printf ("Skipping zone base dn creation for %s\n", argzone);
    }

  for (tmp = ldap_info_base; tmp != NULL; tmp = tmp->next)
    {

      if (debug)
	printf ("Adding DN: %s\n", tmp->dn);

      add_ldap_values (tmp);
    }

  if (debug)
	printf("Operation Complete.\n");

  /* Cleanup */
  isc_hash_destroy();
  isc_entropy_detach(&ectx);
  isc_mem_destroy(&mctx);
  if (zonefile)
	free(zonefile);

  return 0;
}
Ejemplo n.º 22
0
int
main(int argc, char **argv) {
    char *porigin, *zonefile;
    dns_fixedname_t forigin, fname;
    dns_name_t *origin, *name;
    dns_db_t *db = NULL;
    dns_dbiterator_t *dbiter;
    dns_dbnode_t *node;
    dns_rdatasetiter_t *rdsiter;
    dns_rdataset_t rdataset;
    dns_rdata_t rdata = DNS_RDATA_INIT;
    isc_mem_t *mctx = NULL;
    isc_entropy_t *ectx = NULL;
    isc_buffer_t b;
    isc_result_t result;
    PGresult *res;

    if (argc != 5) {
        printf("usage: %s origin file dbname dbtable\n", argv[0]);
        printf("Note that dbname must be an existing database.\n");
        exit(1);
    }

    porigin = argv[1];
    zonefile = argv[2];
    dbname = argv[3];
    dbtable = argv[4];

    dns_result_register();

    mctx = NULL;
    result = isc_mem_create(0, 0, &mctx);
    check_result(result, "isc_mem_create");

    result = isc_entropy_create(mctx, &ectx);
    result_check (result, "isc_entropy_create");

    result = isc_hash_create(mctx, ectx, DNS_NAME_MAXWIRE);
    check_result (result, "isc_hash_create");

    isc_buffer_init(&b, porigin, strlen(porigin));
    isc_buffer_add(&b, strlen(porigin));
    dns_fixedname_init(&forigin);
    origin = dns_fixedname_name(&forigin);
    result = dns_name_fromtext(origin, &b, dns_rootname, ISC_FALSE, NULL);
    check_result(result, "dns_name_fromtext");

    db = NULL;
    result = dns_db_create(mctx, "rbt", origin, dns_dbtype_zone,
                           dns_rdataclass_in, 0, NULL, &db);
    check_result(result, "dns_db_create");

    result = dns_db_load(db, zonefile);
    if (result == DNS_R_SEENINCLUDE)
        result = ISC_R_SUCCESS;
    check_result(result, "dns_db_load");

    printf("Connecting to '%s'\n", dbname);
    conn = PQsetdb(NULL, NULL, NULL, NULL, dbname);
    if (PQstatus(conn) == CONNECTION_BAD) {
        fprintf(stderr, "Connection to database '%s' failed: %s\n",
                dbname, PQerrorMessage(conn));
        closeandexit(1);
    }

    snprintf(str, sizeof(str),
             "DROP TABLE %s", dbtable);
    printf("%s\n", str);
    res = PQexec(conn, str);
    if (!res || PQresultStatus(res) != PGRES_COMMAND_OK)
        fprintf(stderr, "DROP TABLE command failed: %s\n",
                PQresultErrorMessage(res));
    PQclear(res);

    snprintf(str, sizeof(str), "BEGIN");
    printf("%s\n", str);
    res = PQexec(conn, str);
    if (!res || PQresultStatus(res) != PGRES_COMMAND_OK) {
        fprintf(stderr, "BEGIN command failed: %s\n",
                PQresultErrorMessage(res));
        PQclear(res);
        closeandexit(1);
    }
    PQclear(res);

    snprintf(str, sizeof(str),
             "CREATE TABLE %s "
             "(NAME TEXT, TTL INTEGER, RDTYPE TEXT, RDATA TEXT)",
             dbtable);
    printf("%s\n", str);
    res = PQexec(conn, str);
    if (!res || PQresultStatus(res) != PGRES_COMMAND_OK) {
        fprintf(stderr, "CREATE TABLE command failed: %s\n",
                PQresultErrorMessage(res));
        PQclear(res);
        closeandexit(1);
    }
    PQclear(res);

    dbiter = NULL;
    result = dns_db_createiterator(db, ISC_FALSE, &dbiter);
    check_result(result, "dns_db_createiterator()");

    result = dns_dbiterator_first(dbiter);
    check_result(result, "dns_dbiterator_first");

    dns_fixedname_init(&fname);
    name = dns_fixedname_name(&fname);
    dns_rdataset_init(&rdataset);
    dns_rdata_init(&rdata);

    while (result == ISC_R_SUCCESS) {
        node = NULL;
        result = dns_dbiterator_current(dbiter, &node, name);
        if (result == ISC_R_NOMORE)
            break;
        check_result(result, "dns_dbiterator_current");

        rdsiter = NULL;
        result = dns_db_allrdatasets(db, node, NULL, 0, &rdsiter);
        check_result(result, "dns_db_allrdatasets");

        result = dns_rdatasetiter_first(rdsiter);

        while (result == ISC_R_SUCCESS) {
            dns_rdatasetiter_current(rdsiter, &rdataset);
            result = dns_rdataset_first(&rdataset);
            check_result(result, "dns_rdataset_first");
            while (result == ISC_R_SUCCESS) {
                dns_rdataset_current(&rdataset, &rdata);
                addrdata(name, rdataset.ttl, &rdata);
                dns_rdata_reset(&rdata);
                result = dns_rdataset_next(&rdataset);
            }
            dns_rdataset_disassociate(&rdataset);
            result = dns_rdatasetiter_next(rdsiter);
        }
        dns_rdatasetiter_destroy(&rdsiter);
        dns_db_detachnode(db, &node);
        result = dns_dbiterator_next(dbiter);
    }

    snprintf(str, sizeof(str), "COMMIT TRANSACTION");
    printf("%s\n", str);
    res = PQexec(conn, str);
    if (!res || PQresultStatus(res) != PGRES_COMMAND_OK) {
        fprintf(stderr, "COMMIT command failed: %s\n",
                PQresultErrorMessage(res));
        PQclear(res);
        closeandexit(1);
    }
    PQclear(res);
    dns_dbiterator_destroy(&dbiter);
    dns_db_detach(&db);
    isc_hash_destroy();
    isc_entropy_detach(&ectx);
    isc_mem_destroy(&mctx);
    closeandexit(0);
    exit(0);
}