Example #1
0
void
key_options_add_modify(nsd_options_t* opt, key_options_t* key)
{
	key_options_t* orig = key_options_find(opt, key->name);
	if(!orig) {
		/* needs to be copied to opt region */
		orig = key_options_create(opt->region);
		orig->name = region_strdup(opt->region, key->name);
		orig->algorithm = region_strdup(opt->region, key->algorithm);
		orig->secret = region_strdup(opt->region, key->secret);
		key_options_setup(opt->region, orig);
		tsig_add_key(orig->tsig_key);
		key_options_insert(opt, orig);
	} else {
		/* modify entries in existing key, and copy to opt region */
		key_options_desetup(opt->region, orig);
		region_recycle(opt->region, orig->algorithm,
			strlen(orig->algorithm)+1);
		orig->algorithm = region_strdup(opt->region, key->algorithm);
		region_recycle(opt->region, orig->secret,
			strlen(orig->secret)+1);
		orig->secret = region_strdup(opt->region, key->secret);
		key_options_setup(opt->region, orig);
	}
}
Example #2
0
static acl_options_t*
copy_acl_list(nsd_options_t* opt, acl_options_t* a)
{
	acl_options_t* b, *blast = NULL, *blist = NULL;
	while(a) {
		b = copy_acl(opt->region, a);
		/* fixup key_options */
		if(b->key_name)
			b->key_options = key_options_find(opt, b->key_name);
		else	b->key_options = NULL;

		/* link as last into list */
		b->next = NULL;
		if(!blist) blist = b;
		else blast->next = b;
		blast = b;
		
		a = a->next;
	}
	return blist;
}
Example #3
0
void
key_options_remove(nsd_options_t* opt, const char* name)
{
	key_options_t* k = key_options_find(opt, name);
	if(!k) return;
	(void)rbtree_delete(opt->keys, name);
	if(k->name)
		region_recycle(opt->region, k->name, strlen(k->name)+1);
	if(k->algorithm)
		region_recycle(opt->region, k->algorithm, strlen(k->algorithm)+1);
	if(k->secret) {
		memset(k->secret, 0xdd, strlen(k->secret)); /* wipe secret! */
		region_recycle(opt->region, k->secret, strlen(k->secret)+1);
	}
	if(k->tsig_key) {
		tsig_del_key(k->tsig_key);
		if(k->tsig_key->name)
			region_recycle(opt->region, (void*)k->tsig_key->name,
				dname_total_size(k->tsig_key->name));
		key_options_desetup(opt->region, k);
		region_recycle(opt->region, k->tsig_key, sizeof(tsig_key_type));
	}
	region_recycle(opt->region, k, sizeof(key_options_t));
}
Example #4
0
int
parse_options_file(nsd_options_t* opt, const char* file,
	void (*err)(void*,const char*), void* err_arg)
{
	FILE *in = 0;
	pattern_options_t* pat;
	acl_options_t* acl;

	if(!cfg_parser) {
		cfg_parser = (config_parser_state_t*)region_alloc(
			opt->region, sizeof(config_parser_state_t));
		cfg_parser->chroot = 0;
	}
	cfg_parser->err = err;
	cfg_parser->err_arg = err_arg;
	cfg_parser->filename = (char*)file;
	cfg_parser->line = 1;
	cfg_parser->errors = 0;
	cfg_parser->server_settings_seen = 0;
	cfg_parser->opt = opt;
	cfg_parser->current_pattern = 0;
	cfg_parser->current_zone = 0;
	cfg_parser->current_key = 0;
	cfg_parser->current_ip_address_option = opt->ip_addresses;
	while(cfg_parser->current_ip_address_option && cfg_parser->current_ip_address_option->next)
		cfg_parser->current_ip_address_option = cfg_parser->current_ip_address_option->next;
	cfg_parser->current_allow_notify = 0;
	cfg_parser->current_request_xfr = 0;
	cfg_parser->current_notify = 0;
	cfg_parser->current_provide_xfr = 0;
	
	in = fopen(cfg_parser->filename, "r");
	if(!in) {
		if(err) {
			char m[MAXSYSLOGMSGLEN];
			snprintf(m, sizeof(m), "Could not open %s: %s\n",
				file, strerror(errno));
			err(err_arg, m);
		} else {
			fprintf(stderr, "Could not open %s: %s\n",
				file, strerror(errno));
		}
		return 0;
	}
	c_in = in;
	c_parse();
	fclose(in);

	opt->configfile = region_strdup(opt->region, file);
	if(cfg_parser->current_pattern) {
		if(!cfg_parser->current_pattern->pname)
			c_error("last pattern has no name");
		else {
			if(!nsd_options_insert_pattern(cfg_parser->opt,
				cfg_parser->current_pattern))
				c_error("duplicate pattern");
		}
	}
	if(cfg_parser->current_zone) {
		if(!cfg_parser->current_zone->name)
			c_error("last zone has no name");
		else {
			if(!nsd_options_insert_zone(opt,
				cfg_parser->current_zone))
				c_error("duplicate zone");
		}
		if(!cfg_parser->current_zone->pattern)
			c_error("last zone has no pattern");
	}
	if(cfg_parser->current_key)
	{
		if(!cfg_parser->current_key->name)
			c_error("last key has no name");
		if(!cfg_parser->current_key->algorithm)
			c_error("last key has no algorithm");
		if(!cfg_parser->current_key->secret)
			c_error("last key has no secret blob");
		key_options_insert(opt, cfg_parser->current_key);
	}
	RBTREE_FOR(pat, pattern_options_t*, opt->patterns)
	{
		/* lookup keys for acls */
		for(acl=pat->allow_notify; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in pattern %s could not be found",
					acl->key_name, pat->pname);
		}
		for(acl=pat->notify; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in pattern %s could not be found",
					acl->key_name, pat->pname);
		}
		for(acl=pat->request_xfr; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in pattern %s could not be found",
					acl->key_name, pat->pname);
		}
		for(acl=pat->provide_xfr; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in pattern %s could not be found",
					acl->key_name, pat->pname);
		}
	}

	if(cfg_parser->errors > 0)
	{
		if(err) {
			char m[MAXSYSLOGMSGLEN];
			snprintf(m, sizeof(m), "read %s failed: %d errors in "
				"configuration file\n", file,
				cfg_parser->errors);
			err(err_arg, m);
		} else {
			fprintf(stderr, "read %s failed: %d errors in "
				"configuration file\n", file,
				cfg_parser->errors);
		}
		return 0;
	}
	return 1;
}
Example #5
0
int parse_options_file(nsd_options_t* opt, const char* file)
{
	FILE *in = 0;
	zone_options_t* zone;
	acl_options_t* acl;

	if(!cfg_parser)
		cfg_parser = (config_parser_state_t*)region_alloc(
			opt->region, sizeof(config_parser_state_t));
	cfg_parser->filename = file;
	cfg_parser->line = 1;
	cfg_parser->errors = 0;
	cfg_parser->opt = opt;
	cfg_parser->current_zone = 0;
	cfg_parser->current_key = opt->keys;
	while(cfg_parser->current_key && cfg_parser->current_key->next)
		cfg_parser->current_key = cfg_parser->current_key->next;
	cfg_parser->current_ip_address_option = opt->ip_addresses;
	while(cfg_parser->current_ip_address_option && cfg_parser->current_ip_address_option->next)
		cfg_parser->current_ip_address_option = cfg_parser->current_ip_address_option->next;
	cfg_parser->current_allow_notify = 0;
	cfg_parser->current_request_xfr = 0;
	cfg_parser->current_notify = 0;
	cfg_parser->current_provide_xfr = 0;

	in = fopen(cfg_parser->filename, "r");
	if(!in) {
		fprintf(stderr, "Could not open %s: %s\n", file, strerror(errno));
		return 0;
	}
	c_in = in;
	c_parse();
	fclose(in);

	if(cfg_parser->current_zone) {
		if(!cfg_parser->current_zone->name)
			c_error("last zone has no name");
		else {
			if(!nsd_options_insert_zone(opt,
				cfg_parser->current_zone))
				c_error("duplicate zone");
		}
		if(!cfg_parser->current_zone->zonefile)
			c_error("last zone has no zonefile");
	}
	if(opt->keys)
	{
		if(!opt->keys->name)
			c_error("last key has no name");
		if(!opt->keys->algorithm)
			c_error("last key has no algorithm");
		if(!opt->keys->secret)
			c_error("last key has no secret blob");
	}
	RBTREE_FOR(zone, zone_options_t*, opt->zone_options)
	{
		if(!zone->name)
			continue;
		if(!zone->zonefile)
			continue;
		/* lookup keys for acls */
		for(acl=zone->allow_notify; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in zone %s could not be found",
					acl->key_name, zone->name);
		}
		for(acl=zone->notify; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in zone %s could not be found",
					acl->key_name, zone->name);
		}
		for(acl=zone->request_xfr; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in zone %s could not be found",
					acl->key_name, zone->name);
		}
		for(acl=zone->provide_xfr; acl; acl=acl->next)
		{
			if(acl->nokey || acl->blocked)
				continue;
			acl->key_options = key_options_find(opt, acl->key_name);
			if(!acl->key_options)
				c_error_msg("key %s in zone %s could not be found",
					acl->key_name, zone->name);
		}
	}

	if(cfg_parser->errors > 0)
	{
        	fprintf(stderr, "read %s failed: %d errors in configuration file\n",
			cfg_parser->filename,
			cfg_parser->errors);
		return 0;
	}
	return 1;
}