mirror of
https://gitlab.isc.org/isc-projects/bind9
synced 2025-08-29 13:38:26 +00:00
4542. [func] Allow rndc to manipulate redirect zones with using
-redirect as the zone name (use "-redirect." to manipulate a zone named "-redirect"). [RT #43971]
This commit is contained in:
parent
d029dfe95c
commit
5093e8d482
4
CHANGES
4
CHANGES
@ -1,3 +1,7 @@
|
||||
4542. [func] Allow rndc to manipulate redirect zones with using
|
||||
-redirect as the zone name (use "-redirect." to
|
||||
manipulate a zone named "-redirect"). [RT #43971]
|
||||
|
||||
4541. [bug] rndc addzone should properly reject non master/slave
|
||||
zones. [RT #43665]
|
||||
|
||||
|
@ -8917,6 +8917,7 @@ zone_from_args(ns_server_t *server, isc_lex_t *lex, const char *zonetxt,
|
||||
dns_rdataclass_t rdclass;
|
||||
char problem[DNS_NAME_FORMATSIZE + 500] = "";
|
||||
char zonebuf[DNS_NAME_FORMATSIZE];
|
||||
isc_boolean_t redirect = ISC_FALSE;
|
||||
|
||||
REQUIRE(zonep != NULL && *zonep == NULL);
|
||||
|
||||
@ -8934,6 +8935,11 @@ zone_from_args(ns_server_t *server, isc_lex_t *lex, const char *zonetxt,
|
||||
return (ISC_R_SUCCESS);
|
||||
|
||||
/* Copy zonetxt because it'll be overwritten by next_token() */
|
||||
/* To locate a zone named "-redirect" use "-redirect." */
|
||||
if (strcmp(zonetxt, "-redirect") == 0) {
|
||||
redirect = ISC_TRUE;
|
||||
strlcpy(zonebuf, ".", DNS_NAME_FORMATSIZE);
|
||||
} else
|
||||
strlcpy(zonebuf, zonetxt, DNS_NAME_FORMATSIZE);
|
||||
if (zonename != NULL)
|
||||
strlcpy(zonename, zonetxt, DNS_NAME_FORMATSIZE);
|
||||
@ -8956,8 +8962,25 @@ zone_from_args(ns_server_t *server, isc_lex_t *lex, const char *zonetxt,
|
||||
rdclass = dns_rdataclass_in;
|
||||
|
||||
if (viewtxt == NULL) {
|
||||
result = dns_viewlist_findzone(&server->viewlist, name,
|
||||
ISC_TF(classtxt == NULL),
|
||||
if (redirect) {
|
||||
result = dns_viewlist_find(&server->viewlist,
|
||||
"_default",
|
||||
dns_rdataclass_in,
|
||||
&view);
|
||||
if (result != ISC_R_SUCCESS ||
|
||||
view->redirect == NULL)
|
||||
{
|
||||
result = ISC_R_NOTFOUND;
|
||||
snprintf(problem, sizeof(problem),
|
||||
"redirect zone not found in "
|
||||
"_default view");
|
||||
} else {
|
||||
dns_zone_attach(view->redirect, zonep);
|
||||
result = ISC_R_SUCCESS;
|
||||
}
|
||||
} else {
|
||||
result = dns_viewlist_findzone(&server->viewlist,
|
||||
name, ISC_TF(classtxt == NULL),
|
||||
rdclass, zonep);
|
||||
if (result == ISC_R_NOTFOUND)
|
||||
snprintf(problem, sizeof(problem),
|
||||
@ -8965,8 +8988,9 @@ zone_from_args(ns_server_t *server, isc_lex_t *lex, const char *zonetxt,
|
||||
zonebuf);
|
||||
else if (result == ISC_R_MULTIPLE)
|
||||
snprintf(problem, sizeof(problem),
|
||||
"zone '%s' was found in multiple views",
|
||||
zonebuf);
|
||||
"zone '%s' was found in multiple "
|
||||
"views", zonebuf);
|
||||
}
|
||||
} else {
|
||||
result = dns_viewlist_find(&server->viewlist, viewtxt,
|
||||
rdclass, &view);
|
||||
@ -8976,7 +9000,15 @@ zone_from_args(ns_server_t *server, isc_lex_t *lex, const char *zonetxt,
|
||||
goto report;
|
||||
}
|
||||
|
||||
result = dns_zt_find(view->zonetable, name, 0, NULL, zonep);
|
||||
if (redirect) {
|
||||
if (view->redirect != NULL) {
|
||||
dns_zone_attach(view->redirect, zonep);
|
||||
result = ISC_R_SUCCESS;
|
||||
} else
|
||||
result = ISC_R_NOTFOUND;
|
||||
} else
|
||||
result = dns_zt_find(view->zonetable, name, 0,
|
||||
NULL, zonep);
|
||||
if (result != ISC_R_SUCCESS)
|
||||
snprintf(problem, sizeof(problem),
|
||||
"no matching zone '%s' in view '%s'",
|
||||
@ -11246,10 +11278,11 @@ migrate_nzf(dns_view_t *view) {
|
||||
static isc_result_t
|
||||
newzone_parse(ns_server_t *server, char *command, dns_view_t **viewp,
|
||||
cfg_obj_t **zoneconfp, const cfg_obj_t **zoneobjp,
|
||||
isc_buffer_t **text)
|
||||
isc_boolean_t *redirectp, isc_buffer_t **text)
|
||||
{
|
||||
isc_result_t result;
|
||||
isc_buffer_t argbuf;
|
||||
isc_boolean_t redirect = ISC_FALSE;
|
||||
cfg_obj_t *zoneconf = NULL;
|
||||
const cfg_obj_t *zlist = NULL;
|
||||
const cfg_obj_t *zoneobj = NULL;
|
||||
@ -11263,6 +11296,7 @@ newzone_parse(ns_server_t *server, char *command, dns_view_t **viewp,
|
||||
REQUIRE(viewp != NULL && *viewp == NULL);
|
||||
REQUIRE(zoneobjp != NULL && *zoneobjp == NULL);
|
||||
REQUIRE(zoneconfp != NULL && *zoneconfp == NULL);
|
||||
REQUIRE(redirectp != NULL);
|
||||
|
||||
/* Try to parse the argument string */
|
||||
isc_buffer_init(&argbuf, command, (unsigned int) strlen(command));
|
||||
@ -11309,7 +11343,6 @@ newzone_parse(ns_server_t *server, char *command, dns_view_t **viewp,
|
||||
|
||||
if (strcasecmp(cfg_obj_asstring(obj), "hint") == 0 ||
|
||||
strcasecmp(cfg_obj_asstring(obj), "forward") == 0 ||
|
||||
strcasecmp(cfg_obj_asstring(obj), "redirect") == 0 ||
|
||||
strcasecmp(cfg_obj_asstring(obj), "delegation-only") == 0)
|
||||
{
|
||||
(void) putstr(text, "'");
|
||||
@ -11319,6 +11352,9 @@ newzone_parse(ns_server_t *server, char *command, dns_view_t **viewp,
|
||||
CHECK(ISC_R_FAILURE);
|
||||
}
|
||||
|
||||
if (strcasecmp(cfg_obj_asstring(obj), "redirect") == 0)
|
||||
redirect = ISC_TRUE;
|
||||
|
||||
/* Make sense of optional class argument */
|
||||
obj = cfg_tuple_get(zoneobj, "class");
|
||||
CHECK(ns_config_getclass(obj, dns_rdataclass_in, &rdclass));
|
||||
@ -11343,6 +11379,7 @@ newzone_parse(ns_server_t *server, char *command, dns_view_t **viewp,
|
||||
*viewp = view;
|
||||
*zoneobjp = zoneobj;
|
||||
*zoneconfp = zoneconf;
|
||||
*redirectp = redirect;
|
||||
|
||||
return (ISC_R_SUCCESS);
|
||||
|
||||
@ -11420,7 +11457,7 @@ delete_zoneconf(dns_view_t *view, cfg_parser_t *pctx,
|
||||
static isc_result_t
|
||||
do_addzone(ns_server_t *server, ns_cfgctx_t *cfg, dns_view_t *view,
|
||||
dns_name_t *name, cfg_obj_t *zoneconf, const cfg_obj_t *zoneobj,
|
||||
isc_buffer_t **text)
|
||||
isc_boolean_t redirect, isc_buffer_t **text)
|
||||
{
|
||||
isc_result_t result, tresult;
|
||||
dns_zone_t *zone = NULL;
|
||||
@ -11434,6 +11471,10 @@ do_addzone(ns_server_t *server, ns_cfgctx_t *cfg, dns_view_t *view,
|
||||
#endif /* HAVE_LMDB */
|
||||
|
||||
/* Zone shouldn't already exist */
|
||||
if (redirect) {
|
||||
result = (view->redirect != NULL) ? ISC_R_SUCCESS :
|
||||
ISC_R_NOTFOUND;
|
||||
} else
|
||||
result = dns_zt_find(view->zonetable, name, 0, NULL, &zone);
|
||||
if (result == ISC_R_SUCCESS) {
|
||||
result = ISC_R_EXISTS;
|
||||
@ -11491,6 +11532,11 @@ do_addzone(ns_server_t *server, ns_cfgctx_t *cfg, dns_view_t *view,
|
||||
}
|
||||
|
||||
/* Is it there yet? */
|
||||
if (redirect) {
|
||||
if (view->redirect == NULL)
|
||||
CHECK(ISC_R_NOTFOUND);
|
||||
dns_zone_attach(view->redirect, &zone);
|
||||
} else
|
||||
CHECK(dns_zt_find(view->zonetable, name, 0, NULL, &zone));
|
||||
|
||||
#ifndef HAVE_LMDB
|
||||
@ -11565,7 +11611,7 @@ do_addzone(ns_server_t *server, ns_cfgctx_t *cfg, dns_view_t *view,
|
||||
static isc_result_t
|
||||
do_modzone(ns_server_t *server, ns_cfgctx_t *cfg, dns_view_t *view,
|
||||
dns_name_t *name, const char *zname, const cfg_obj_t *zoneobj,
|
||||
isc_buffer_t **text)
|
||||
isc_boolean_t redirect, isc_buffer_t **text)
|
||||
{
|
||||
isc_result_t result, tresult;
|
||||
dns_zone_t *zone = NULL;
|
||||
@ -11580,6 +11626,13 @@ do_modzone(ns_server_t *server, ns_cfgctx_t *cfg, dns_view_t *view,
|
||||
#endif /* HAVE_LMDB */
|
||||
|
||||
/* Zone must already exist */
|
||||
if (redirect) {
|
||||
if (view->redirect != NULL) {
|
||||
dns_zone_attach(view->redirect, &zone);
|
||||
result = ISC_R_SUCCESS;
|
||||
} else
|
||||
result = ISC_R_NOTFOUND;
|
||||
} else
|
||||
result = dns_zt_find(view->zonetable, name, 0, NULL, &zone);
|
||||
if (result != ISC_R_SUCCESS)
|
||||
goto cleanup;
|
||||
@ -11640,8 +11693,15 @@ do_modzone(ns_server_t *server, ns_cfgctx_t *cfg, dns_view_t *view,
|
||||
}
|
||||
|
||||
/* Is it there yet? */
|
||||
if (redirect) {
|
||||
if (view->redirect == NULL)
|
||||
CHECK(ISC_R_NOTFOUND);
|
||||
dns_zone_attach(view->redirect, &zone);
|
||||
} else
|
||||
CHECK(dns_zt_find(view->zonetable, name, 0, NULL, &zone));
|
||||
|
||||
|
||||
|
||||
#ifndef HAVE_LMDB
|
||||
/* Remove old zone from configuration (and NZF file if applicable) */
|
||||
if (added) {
|
||||
@ -11770,6 +11830,7 @@ isc_result_t
|
||||
ns_server_changezone(ns_server_t *server, char *command, isc_buffer_t **text) {
|
||||
isc_result_t result;
|
||||
isc_boolean_t addzone;
|
||||
isc_boolean_t redirect = ISC_FALSE;
|
||||
ns_cfgctx_t *cfg = NULL;
|
||||
cfg_obj_t *zoneconf = NULL;
|
||||
const cfg_obj_t *zoneobj = NULL;
|
||||
@ -11787,7 +11848,7 @@ ns_server_changezone(ns_server_t *server, char *command, isc_buffer_t **text) {
|
||||
}
|
||||
|
||||
CHECK(newzone_parse(server, command, &view, &zoneconf,
|
||||
&zoneobj, text));
|
||||
&zoneobj, &redirect, text));
|
||||
|
||||
/* Are we accepting new zones in this view? */
|
||||
#ifdef HAVE_LMDB
|
||||
@ -11817,12 +11878,20 @@ ns_server_changezone(ns_server_t *server, char *command, isc_buffer_t **text) {
|
||||
dnsname = dns_fixedname_name(&fname);
|
||||
CHECK(dns_name_fromtext(dnsname, &buf, dns_rootname, 0, NULL));
|
||||
|
||||
if (redirect) {
|
||||
if (!dns_name_equal(dnsname, dns_rootname)) {
|
||||
(void) putstr(text,
|
||||
"redirect zones must be called \".\"");
|
||||
CHECK(ISC_R_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
if (addzone)
|
||||
CHECK(do_addzone(server, cfg, view, dnsname, zoneconf,
|
||||
zoneobj, text));
|
||||
zoneobj, redirect, text));
|
||||
else
|
||||
CHECK(do_modzone(server, cfg, view, dnsname, zonename,
|
||||
zoneobj, text));
|
||||
zoneobj, redirect, text));
|
||||
|
||||
isc_log_write(ns_g_lctx, NS_LOGCATEGORY_GENERAL,
|
||||
NS_LOGMODULE_SERVER, ISC_LOG_INFO,
|
||||
@ -12054,6 +12123,9 @@ ns_server_delzone(ns_server_t *server, isc_lex_t *lex, isc_buffer_t **text) {
|
||||
}
|
||||
|
||||
view = dns_zone_getview(zone);
|
||||
if (dns_zone_gettype(zone) == dns_zone_redirect)
|
||||
dns_zone_detach(&view->redirect);
|
||||
else
|
||||
CHECK(dns_zt_unmount(view->zonetable, zone));
|
||||
|
||||
/* Send cleanup event */
|
||||
|
@ -968,6 +968,19 @@
|
||||
</varlistentry>
|
||||
|
||||
</variablelist>
|
||||
|
||||
<para>
|
||||
<command>rndc</command> commands that specify zone names,
|
||||
such as <command>reload</command>, <command>retransfer</command>
|
||||
or <command>zonestatus</command>, can be ambiguous when applied
|
||||
to zones of type <option>redirect</option>. Redirect zones are
|
||||
always called ".", and can be confused with zones of type
|
||||
<option>hint</option> or with slaved copies of the root zone.
|
||||
To specify a redirect zone, use the special zone name
|
||||
<userinput>-redirect</userinput>, without a trailing period.
|
||||
(With a trailing period, this would specify a zone called
|
||||
"-redirect".)
|
||||
</para>
|
||||
</refsection>
|
||||
|
||||
<refsection><info><title>LIMITATIONS</title></info>
|
||||
|
@ -306,18 +306,30 @@ n=`expr $n + 1`
|
||||
if [ $ret != 0 ]; then echo "I:failed"; fi
|
||||
status=`expr $status + $ret`
|
||||
|
||||
echo "I:check that zone type 'redirect' (master) is properly rejected ($n)"
|
||||
echo "I:check that adding a 'master redirect' zone works ($n)"
|
||||
ret=0
|
||||
$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p 9953 addzone '"." { type redirect; file "redirect.db"; };' > rndc.out.ns2.$n 2>&1 && ret=1
|
||||
grep "zones not supported by addzone" rndc.out.ns2.$n > /dev/null || ret=1
|
||||
$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p 9953 addzone '"." { type redirect; file "redirect.db"; };' > rndc.out.ns2.$n 2>&1 || ret=1
|
||||
n=`expr $n + 1`
|
||||
if [ $ret != 0 ]; then echo "I:failed"; fi
|
||||
status=`expr $status + $ret`
|
||||
|
||||
echo "I:check that zone type 'redirect' (slave) is properly rejected ($n)"
|
||||
echo "I:check that deleting a 'master redirect' zone works ($n)"
|
||||
ret=0
|
||||
$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p 9953 addzone '"." { type redirect; masters { 1.2.3.4; }; file "redirect.bk"; };' > rndc.out.ns2.$n 2>&1 && ret=1
|
||||
grep "zones not supported by addzone" rndc.out.ns2.$n > /dev/null || ret=1
|
||||
$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p 9953 delzone -redirect > rndc.out.ns2.$n 2>&1 || ret=1
|
||||
n=`expr $n + 1`
|
||||
if [ $ret != 0 ]; then echo "I:failed"; fi
|
||||
status=`expr $status + $ret`
|
||||
|
||||
echo "I:check that adding a 'slave redirect' zone works ($n)"
|
||||
ret=0
|
||||
$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p 9953 addzone '"." { type redirect; masters { 1.2.3.4; }; file "redirect.bk"; };' > rndc.out.ns2.$n 2>&1 || ret=1
|
||||
n=`expr $n + 1`
|
||||
if [ $ret != 0 ]; then echo "I:failed"; fi
|
||||
status=`expr $status + $ret`
|
||||
|
||||
echo "I:check that deleting a 'slave redirect' zone works ($n)"
|
||||
ret=0
|
||||
$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p 9953 delzone -redirect > rndc.out.ns2.$n 2>&1 || ret=1
|
||||
n=`expr $n + 1`
|
||||
if [ $ret != 0 ]; then echo "I:failed"; fi
|
||||
status=`expr $status + $ret`
|
||||
|
@ -62,6 +62,13 @@
|
||||
<userinput>local</userinput>. [RT #42585]
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<para>
|
||||
Rndc commands can now manipulate redirect zones using "-redirect".
|
||||
To manipulate a zone called "-redirect" reference it using absolute
|
||||
name form ("-redirect.").
|
||||
</para>
|
||||
</listitem>
|
||||
</itemizedlist>
|
||||
</section>
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user