1#!/bin/sh -x
2
3# Copyright (C) Internet Systems Consortium, Inc. ("ISC")
4#
5# SPDX-License-Identifier: MPL-2.0
6#
7# This Source Code Form is subject to the terms of the Mozilla Public
8# License, v. 2.0.  If a copy of the MPL was not distributed with this
9# file, you can obtain one at https://mozilla.org/MPL/2.0/.
10#
11# See the COPYRIGHT file distributed with this work for additional
12# information regarding copyright ownership.
13
14set -e
15
16# shellcheck source=conf.sh
17SYSTEMTESTTOP=..
18. "$SYSTEMTESTTOP/conf.sh"
19
20dig_with_opts() {
21	"$DIG" -p "${PORT}" "$@"
22}
23
24rndccmd() (
25	"$RNDC" -c "$SYSTEMTESTTOP/common/rndc.conf" -p "${CONTROLPORT}" -s "$@"
26)
27
28_wait_for_message() (
29	nextpartpeek "$1" > wait_for_message.$n
30	grep -F "$2" wait_for_message.$n >/dev/null
31)
32
33wait_for_message() (
34	retry_quiet 20 _wait_for_message "$@"
35)
36
37_wait_for_rcode() (
38	rcode="$1"
39	qtype="$2"
40	ns="$3"
41	qname="$4"
42	file="$5"
43	shift 5
44	dig_with_opts "$ns" "$qtype" "$qname" "$@" >"$file" || return 1
45	grep "status: $rcode" "$file" >/dev/null
46)
47
48wait_for_rcode() (
49	retry_quiet 10 _wait_for_rcode "$@"
50)
51
52wait_for_soa() (
53	wait_for_rcode NOERROR SOA "$@"
54)
55
56wait_for_a() (
57	wait_for_rcode NOERROR A "$@"
58)
59
60wait_for_no_soa() {
61	wait_for_rcode REFUSED SOA "$@"
62}
63
64_wait_for_zonefile() (
65	# shellcheck disable=SC2234
66	[ -f "$1" ]
67)
68
69wait_for_zonefile() (
70	retry_quiet 10 _wait_for_zonefile "$@"
71)
72
73_wait_for_no_zonefile() (
74	# shellcheck disable=SC2234
75	[ ! -f "$1" ]
76)
77
78wait_for_no_zonefile() (
79	retry_quiet 10 _wait_for_no_zonefile "$@"
80)
81
82status=0
83n=0
84##########################################################################
85echo_i "Testing adding/removing of domain in catalog zone"
86n=$((n+1))
87echo_i "checking that dom1.example. is not served by primary ($n)"
88ret=0
89wait_for_no_soa @10.53.0.1 dom1.example. dig.out.test$n || ret=1
90if [ $ret -ne 0 ]; then echo_i "failed"; fi
91status=$((status+ret))
92
93n=$((n+1))
94echo_i "Adding a domain dom1.example. to primary via RNDC ($n)"
95ret=0
96# enough initial content for IXFR response when TXT record is added below
97echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom1.example.db
98echo "@ 3600 IN NS invalid." >> ns1/dom1.example.db
99echo "foo 3600 IN TXT some content here" >> ns1/dom1.example.db
100echo "bar 3600 IN TXT some content here" >> ns1/dom1.example.db
101echo "xxx 3600 IN TXT some content here" >> ns1/dom1.example.db
102echo "yyy 3600 IN TXT some content here" >> ns1/dom1.example.db
103rndccmd 10.53.0.1 addzone dom1.example. '{ type primary; file "dom1.example.db"; allow-update { any; }; notify explicit; also-notify { 10.53.0.2; }; };' || ret=1
104if [ $ret -ne 0 ]; then echo_i "failed"; fi
105status=$((status+ret))
106
107n=$((n+1))
108echo_i "checking that dom1.example. is now served by primary ($n)"
109ret=0
110wait_for_soa @10.53.0.1 dom1.example. dig.out.test$n || ret=1
111if [ $ret -ne 0 ]; then echo_i "failed"; fi
112status=$((status+ret))
113
114nextpart ns2/named.run >/dev/null
115
116n=$((n+1))
117echo_i "Adding domain dom1.example. to catalog1 zone ($n)"
118ret=0
119$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
120    server 10.53.0.1 ${PORT}
121    update add e721433b6160b450260d4f54b3ec8bab30cb3b83.zones.catalog1.example. 3600 IN PTR dom1.example.
122    send
123END
124if [ $ret -ne 0 ]; then echo_i "failed"; fi
125status=$((status+ret))
126
127n=$((n+1))
128echo_i "waiting for secondary to sync up ($n)"
129ret=0
130wait_for_message ns2/named.run "catz: adding zone 'dom1.example' from catalog 'catalog1.example'" &&
131wait_for_message ns2/named.run "transfer of 'dom1.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
132if [ $ret -ne 0 ]; then echo_i "failed"; fi
133status=$((status+ret))
134
135n=$((n+1))
136echo_i "checking that dom1.example. is served by secondary ($n)"
137ret=0
138wait_for_soa @10.53.0.2 dom1.example. dig.out.test$n || ret=1
139if [ $ret -ne 0 ]; then echo_i "failed"; fi
140status=$((status+ret))
141
142n=$((n+1))
143echo_i "checking that zone-directory is populated ($n)"
144ret=0
145wait_for_zonefile "ns2/zonedir/__catz___default_catalog1.example_dom1.example.db" || ret=1
146if [ $ret -ne 0 ]; then echo_i "failed"; fi
147status=$((status+ret))
148
149n=$((n+1))
150echo_i "update dom1.example. ($n)"
151ret=0
152$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
153   server 10.53.0.1 ${PORT}
154   update add dom1.example 0 IN TXT added record
155   send
156END
157if [ $ret -ne 0 ]; then echo_i "failed"; fi
158status=$((status+ret))
159
160n=$((n+1))
161echo_i "wait for secondary to be updated ($n)"
162ret=0
163wait_for_txt() {
164	dig_with_opts @10.53.0.2 TXT dom1.example. > dig.out.test$n || return 1
165	grep "ANSWER: 1," dig.out.test$n > /dev/null || return 1
166	grep "status: NOERROR" dig.out.test$n > /dev/null || return 1
167	grep "IN.TXT." dig.out.test$n > /dev/null || return 1
168}
169retry_quiet 10 wait_for_txt || ret=1
170if [ $ret -ne 0 ]; then echo_i "failed"; fi
171status=$((status+ret))
172
173n=$((n+1))
174echo_i "check that journal was created for cleanup test ($n)"
175ret=0
176test -f ns2/zonedir/__catz___default_catalog1.example_dom1.example.db.jnl || ret=1
177if [ $ret -ne 0 ]; then echo_i "failed"; fi
178status=$((status+ret))
179
180n=$((n+1))
181echo_i "update catalog zone serial ($n)"
182ret=0
183# default minimum update rate is once / 5 seconds
184sleep 5
185$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
186    server 10.53.0.1 ${PORT}
187    update add catalog1.example 3600 SOA . . 20 86400 3600 86400 3600
188    send
189END
190if [ $ret -ne 0 ]; then echo_i "failed"; fi
191status=$((status+ret))
192
193n=$((n+1))
194echo_i "wait for catalog zone to transfer ($n)"
195ret=0
196wait_for_soa_equal_20() {
197	dig_with_opts @10.53.0.2 SOA catalog1.example. > dig.out.test$n || return 1
198	grep "ANSWER: 1," dig.out.test$n > /dev/null || return 1
199	grep "status: NOERROR" dig.out.test$n > /dev/null || return 1
200	grep 'IN.SOA.\. \. 20 ' dig.out.test$n > /dev/null || return 1
201}
202retry_quiet 10 wait_for_soa_equal_20 || ret=1
203if [ $ret -ne 0 ]; then echo_i "failed"; fi
204status=$((status+ret))
205
206n=$((n+1))
207echo_i "update dom1.example. again ($n)"
208ret=0
209$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
210   server 10.53.0.1 ${PORT}
211   update add foo.dom1.example 0 IN TXT added record
212   send
213END
214if [ $ret -ne 0 ]; then echo_i "failed"; fi
215status=$((status+ret))
216
217n=$((n+1))
218echo_i "wait for secondary to be updated again ($n)"
219ret=0
220wait_for_txt() {
221	dig_with_opts @10.53.0.2 TXT foo.dom1.example. > dig.out.test$n || return 1
222	grep "ANSWER: 2," dig.out.test$n > /dev/null || return 1
223	grep "status: NOERROR" dig.out.test$n > /dev/null || return 1
224	grep "IN.TXT." dig.out.test$n > /dev/null || return 1
225}
226retry_quiet 10 wait_for_txt || ret=1
227if [ $ret -ne 0 ]; then echo_i "failed"; fi
228status=$((status+ret))
229
230n=$((n+1))
231echo_i "removing domain dom1.example. from catalog1 zone ($n)"
232ret=0
233$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
234   server 10.53.0.1 ${PORT}
235   update delete e721433b6160b450260d4f54b3ec8bab30cb3b83.zones.catalog1.example
236   send
237END
238if [ $ret -ne 0 ]; then echo_i "failed"; fi
239status=$((status+ret))
240
241n=$((n+1))
242echo_i "waiting for secondary to sync up ($n)"
243ret=0
244wait_for_message ns2/named.run "zone_shutdown: zone dom1.example/IN: shutting down" || ret=1
245if [ $ret -ne 0 ]; then echo_i "failed"; fi
246status=$((status+ret))
247
248n=$((n+1))
249echo_i "checking that dom1.example. is not served by secondary ($n)"
250ret=0
251wait_for_no_soa @10.53.0.2 dom1.example. dig.out.test$n || ret=1
252if [ $ret -ne 0 ]; then echo_i "failed"; fi
253status=$((status+ret))
254
255n=$((n+1))
256echo_i "checking that zone-directory is emptied ($n)"
257ret=0
258wait_for_no_zonefile "ns2/zonedir/__catz___default_catalog1.example_dom1.example.db" || ret=1
259wait_for_no_zonefile "ns2/zonedir/__catz___default_catalog1.example_dom1.example.db.jnl" || ret=1
260if [ $ret -ne 0 ]; then echo_i "failed"; fi
261status=$((status+ret))
262
263##########################################################################
264echo_i "Testing various simple operations on domains, including using multiple catalog zones and garbage in zone"
265n=$((n+1))
266echo_i "adding domain dom2.example. to primary via RNDC ($n)"
267ret=0
268echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom2.example.db
269echo "@ IN NS invalid." >> ns1/dom2.example.db
270rndccmd 10.53.0.1 addzone dom2.example. '{type primary; file "dom2.example.db";};' || ret=1
271if [ $ret -ne 0 ]; then echo_i "failed"; fi
272status=$((status+ret))
273
274n=$((n+1))
275echo_i "adding domain dom4.example. to primary via RNDC ($n)"
276ret=0
277echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom4.example.db
278echo "@ IN NS invalid." >> ns1/dom4.example.db
279rndccmd 10.53.0.1 addzone dom4.example. '{type primary; file "dom4.example.db";};' || ret=1
280if [ $ret -ne 0 ]; then echo_i "failed"; fi
281status=$((status+ret))
282
283n=$((n+1))
284echo_i "adding domains dom2.example, dom3.example. and some garbage to catalog1 zone ($n)"
285ret=0
286$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
287    server 10.53.0.1 ${PORT}
288    update add 636722929740e507aaf27c502812fc395d30fb17.zones.catalog1.example. 3600 IN PTR dom2.example.
289    update add b901f492f3ebf6c1e5b597e51766f02f0479eb03.zones.catalog1.example. 3600 IN PTR dom3.example.
290    update add e721433b6160b450260d4f54b3ec8bab30cb3b83.zones.catalog1.example. 3600 IN NS foo.bar.
291    update add trash.catalog1.example. 3600 IN A 1.2.3.4
292    update add trash2.foo.catalog1.example. 3600 IN A 1.2.3.4
293    update add trash3.zones.catalog1.example. 3600 IN NS a.dom2.example.
294    update add foobarbaz.b901f492f3ebf6c1e5b597e51766f02f0479eb03.zones.catalog1.example. 3600 IN PTR dom3.example.
295    update add blahblah.636722929740e507aaf27c502812fc395d30fb17.zones.catalog1.example. 3600 IN PTR dom2.example.
296    update add foobarbaz.b901f492f3ebf6c1e5b597e51766f02f0479eb03.zones.catalog1.example. 3600 IN APL 1:1.2.3.4/30
297    update add blahblah.636722929740e507aaf27c502812fc395d30fb17.zones.catalog1.example. 3600 IN TXT "blah blah"
298    update add version.catalog1.example. 3600 IN A 1.2.3.4
299    send
300
301END
302if [ $ret -ne 0 ]; then echo_i "failed"; fi
303status=$((status+ret))
304
305n=$((n+1))
306echo_i "adding domain dom4.example. to catalog2 zone ($n)"
307ret=0
308$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
309    server 10.53.0.3 ${PORT}
310    update add de26b88d855397a03f77ff1162fd055d8b419584.zones.catalog2.example. 3600 IN PTR dom4.example.
311    send
312END
313if [ $ret -ne 0 ]; then echo_i "failed"; fi
314status=$((status+ret))
315
316
317n=$((n+1))
318echo_i "waiting for secondary to sync up ($n)"
319ret=0
320wait_for_message ns2/named.run "catz: updating catalog zone 'catalog2.example' with serial 2670950425" &&
321wait_for_message ns2/named.run "catz: adding zone 'dom2.example' from catalog 'catalog1.example'" &&
322wait_for_message ns2/named.run "catz: adding zone 'dom3.example' from catalog 'catalog1.example'" &&
323wait_for_message ns2/named.run "catz: adding zone 'dom4.example' from catalog 'catalog2.example'" &&
324wait_for_message ns2/named.run "transfer of 'dom4.example/IN' from 10.53.0.1#${EXTRAPORT1}: Transfer status: success" || ret=1
325if [ $ret -ne 0 ]; then echo_i "failed"; fi
326status=$((status+ret))
327
328n=$((n+1))
329echo_i "checking that dom4.example. is served by secondary ($n)"
330ret=0
331wait_for_soa @10.53.0.2 dom4.example. dig.out.test$n || ret=1
332if [ $ret -ne 0 ]; then echo_i "failed"; fi
333status=$((status+ret))
334
335
336n=$((n+1))
337echo_i "checking that dom3.example. is not served by primary ($n)"
338ret=0
339wait_for_no_soa @10.53.0.1 dom3.example. dig.out.test$n || ret=1
340if [ $ret -ne 0 ]; then echo_i "failed"; fi
341status=$((status+ret))
342
343n=$((n+1))
344echo_i "adding a domain dom3.example. to primary via RNDC ($n)"
345ret=0
346echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom3.example.db
347echo "@ IN NS invalid." >> ns1/dom3.example.db
348rndccmd 10.53.0.1 addzone dom3.example. '{type primary; file "dom3.example.db"; also-notify { 10.53.0.2; }; notify explicit; };' || ret=1
349if [ $ret -ne 0 ]; then echo_i "failed"; fi
350status=$((status+ret))
351
352n=$((n+1))
353echo_i "checking that dom3.example. is served by primary ($n)"
354ret=0
355wait_for_soa  @10.53.0.1 dom3.example. dig.out.test$n || ret=1
356if [ $ret -ne 0 ]; then echo_i "failed"; fi
357status=$((status+ret))
358
359n=$((n+1))
360echo_i "waiting for secondary to sync up ($n)"
361ret=0
362wait_for_message ns2/named.run "catz: adding zone 'dom2.example' from catalog 'catalog1.example'" &&
363wait_for_message ns2/named.run "catz: adding zone 'dom3.example' from catalog 'catalog1.example'" &&
364wait_for_message ns2/named.run  "transfer of 'dom2.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" &&
365wait_for_message ns2/named.run  "transfer of 'dom3.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
366if [ $ret -ne 0 ]; then echo_i "failed"; fi
367status=$((status+ret))
368
369n=$((n+1))
370echo_i "checking that dom3.example. is served by secondary ($n)"
371ret=0
372wait_for_soa @10.53.0.2 dom3.example. dig.out.test$n || ret=1
373if [ $ret -ne 0 ]; then echo_i "failed"; fi
374status=$((status+ret))
375
376nextpart ns2/named.run >/dev/null
377
378# GL #3060
379n=$((n+1))
380echo_i "reconfiguring secondary - checking if catz survives a certain class of failed reconfiguration attempts ($n)"
381ret=0
382sed -e "s/^#T3//" < ns2/named1.conf.in > ns2/named.conf.tmp
383copy_setports ns2/named.conf.tmp ns2/named.conf
384$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p "${CONTROLPORT}" reconfig > /dev/null 2>&1 && ret=1
385if [ $ret -ne 0 ]; then echo_i "failed"; fi
386status=$((status+ret))
387
388n=$((n+1))
389echo_i "checking again that dom3.example. is served by secondary ($n)"
390ret=0
391wait_for_soa @10.53.0.2 dom3.example. dig.out.test$n || ret=1
392if [ $ret -ne 0 ]; then echo_i "failed"; fi
393status=$((status+ret))
394
395n=$((n+1))
396echo_i "reconfiguring secondary - reverting the bad configuration ($n)"
397ret=0
398copy_setports ns2/named1.conf.in ns2/named.conf
399rndccmd 10.53.0.2 reconfig || ret=1
400if [ $ret -ne 0 ]; then echo_i "failed"; fi
401status=$((status+ret))
402
403nextpart ns2/named.run >/dev/null
404
405# GL #3911
406n=$((n+1))
407echo_i "reconfiguring secondary - checking if catz survives another type of failed reconfiguration attempts ($n)"
408ret=0
409sed -e "s/^#T4//" < ns2/named1.conf.in > ns2/named.conf.tmp
410copy_setports ns2/named.conf.tmp ns2/named.conf
411$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p "${CONTROLPORT}" reconfig > /dev/null 2>&1 && ret=1
412if [ $ret -ne 0 ]; then echo_i "failed"; fi
413status=$((status+ret))
414
415# catalog zone update can be deferred
416sleep 2
417
418n=$((n+1))
419echo_i "checking again that dom3.example. is served by secondary ($n)"
420ret=0
421wait_for_soa @10.53.0.2 dom3.example. dig.out.test$n || ret=1
422if [ $ret -ne 0 ]; then echo_i "failed"; fi
423status=$((status+ret))
424
425n=$((n+1))
426echo_i "reconfiguring secondary - reverting the bad configuration ($n)"
427ret=0
428copy_setports ns2/named1.conf.in ns2/named.conf
429rndccmd 10.53.0.2 reconfig || ret=1
430if [ $ret -ne 0 ]; then echo_i "failed"; fi
431status=$((status+ret))
432
433nextpart ns2/named.run >/dev/null
434
435n=$((n+1))
436echo_i "removing all records from catalog1 zone ($n)"
437ret=0
438$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
439    server 10.53.0.1 ${PORT}
440    update delete 636722929740e507aaf27c502812fc395d30fb17.zones.catalog1.example. 3600 IN PTR dom2.example.
441    update delete b901f492f3ebf6c1e5b597e51766f02f0479eb03.zones.catalog1.example. 3600 IN PTR dom3.example.
442    update delete e721433b6160b450260d4f54b3ec8bab30cb3b83.zones.catalog1.example. 3600 IN NS foo.bar.
443    update delete trash.catalog1.example. 3600 IN A 1.2.3.4
444    update delete trash2.foo.catalog1.example. 3600 IN A 1.2.3.4
445    update delete trash3.zones.catalog1.example. 3600 IN NS a.dom2.example.
446    update delete foobarbaz.b901f492f3ebf6c1e5b597e51766f02f0479eb03.zones.catalog1.example. 3600 IN PTR dom3.example.
447    update delete blahblah.636722929740e507aaf27c502812fc395d30fb17.zones.catalog1.example. 3600 IN PTR dom2.example.
448    update delete foobarbaz.b901f492f3ebf6c1e5b597e51766f02f0479eb03.zones.catalog1.example. 3600 IN APL 1:1.2.3.4/30
449    update delete blahblah.636722929740e507aaf27c502812fc395d30fb17.zones.catalog1.example. 3600 IN TXT "blah blah"
450    update delete version.catalog1.example. 3600 IN A 1.2.3.4
451    send
452
453END
454if [ $ret -ne 0 ]; then echo_i "failed"; fi
455status=$((status+ret))
456
457n=$((n+1))
458echo_i "removing all records from catalog2 zone ($n)"
459ret=0
460$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
461    server 10.53.0.3 ${PORT}
462    update delete de26b88d855397a03f77ff1162fd055d8b419584.zones.catalog2.example. 3600 IN PTR dom4.example.
463    send
464END
465if [ $ret -ne 0 ]; then echo_i "failed"; fi
466status=$((status+ret))
467
468##########################################################################
469echo_i "Testing masters suboption and random labels"
470n=$((n+1))
471echo_i "adding dom5.example. with a valid masters suboption (IP without TSIG) and a random label ($n)"
472ret=0
473$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
474    server 10.53.0.1 ${PORT}
475    update add somerandomlabel.zones.catalog1.example. 3600 IN PTR dom5.example.
476    update add masters.somerandomlabel.zones.catalog1.example. 3600 IN A 10.53.0.3
477    send
478END
479if [ $ret -ne 0 ]; then echo_i "failed"; fi
480status=$((status+ret))
481
482n=$((n+1))
483echo_i "waiting for secondary to sync up ($n)"
484ret=0
485wait_for_message ns2/named.run  "catz: adding zone 'dom5.example' from catalog 'catalog1.example'" &&
486wait_for_message ns2/named.run  "transfer of 'dom5.example/IN' from 10.53.0.3#${PORT}: Transfer status: success" || ret=1
487if [ $ret -ne 0 ]; then echo_i "failed"; fi
488status=$((status+ret))
489
490n=$((n+1))
491echo_i "checking that dom5.example. is served by secondary ($n)"
492ret=0
493wait_for_soa @10.53.0.2 dom5.example. dig.out.test$n || ret=1
494if [ $ret -ne 0 ]; then echo_i "failed"; fi
495status=$((status+ret))
496
497n=$((n+1))
498echo_i "removing dom5.example. ($n)"
499ret=0
500$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
501    server 10.53.0.1 ${PORT}
502    update delete somerandomlabel.zones.catalog1.example. 3600 IN PTR dom5.example.
503    update delete masters.somerandomlabel.zones.catalog1.example. 3600 IN A 10.53.0.3
504    send
505END
506if [ $ret -ne 0 ]; then echo_i "failed"; fi
507status=$((status+ret))
508
509n=$((n+1))
510echo_i "waiting for secondary to sync up ($n)"
511ret=0
512wait_for_message ns2/named.run  "zone_shutdown: zone dom5.example/IN: shutting down" || ret=1
513if [ $ret -ne 0 ]; then echo_i "failed"; fi
514status=$((status+ret))
515
516n=$((n+1))
517echo_i "checking that dom5.example. is no longer served by secondary ($n)"
518ret=0
519wait_for_no_soa @10.53.0.2 dom5.example. dig.out.test$n || ret=1
520if [ $ret -ne 0 ]; then echo_i "failed"; fi
521status=$((status+ret))
522
523
524##########################################################################
525echo_i "Testing masters global option"
526n=$((n+1))
527echo_i "adding dom6.example. and a valid global masters option (IP without TSIG) ($n)"
528ret=0
529$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
530    server 10.53.0.1 ${PORT}
531    update add masters.catalog1.example. 3600 IN A 10.53.0.3
532    update add masters.catalog1.example. 3600 IN AAAA fd92:7065:b8e:ffff::3
533    update add 4346f565b4d63ddb99e5d2497ff22d04e878e8f8.zones.catalog1.example. 3600 IN PTR dom6.example.
534    send
535END
536if [ $ret -ne 0 ]; then echo_i "failed"; fi
537status=$((status+ret))
538
539n=$((n+1))
540echo_i "waiting for secondary to sync up ($n)"
541ret=0
542wait_for_message ns2/named.run  "catz: adding zone 'dom6.example' from catalog 'catalog1.example'" &&
543wait_for_message ns2/named.run  "transfer of 'dom6.example/IN' from " > /dev/null || ret=1
544if [ $ret -ne 0 ]; then echo_i "failed"; fi
545status=$((status+ret))
546
547n=$((n+1))
548echo_i "checking that dom6.example. is served by secondary ($n)"
549ret=0
550wait_for_soa @10.53.0.2 dom6.example. dig.out.test$n || ret=1
551if [ $ret -ne 0 ]; then echo_i "failed"; fi
552status=$((status+ret))
553
554n=$((n+1))
555echo_i "removing dom6.example. ($n)"
556ret=0
557$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
558    server 10.53.0.1 ${PORT}
559    update delete masters.catalog1.example. 3600 IN A 10.53.0.3
560    update delete masters.catalog1.example. 3600 IN AAAA  fd92:7065:b8e:ffff::3
561    update delete 4346f565b4d63ddb99e5d2497ff22d04e878e8f8.zones.catalog1.example. 3600 IN PTR dom6.example.
562    send
563END
564if [ $ret -ne 0 ]; then echo_i "failed"; fi
565status=$((status+ret))
566
567n=$((n+1))
568echo_i "waiting for secondary to sync up ($n)"
569ret=0
570wait_for_message ns2/named.run  "zone_shutdown: zone dom6.example/IN: shutting down" || ret=1
571if [ $ret -ne 0 ]; then echo_i "failed"; fi
572status=$((status+ret))
573
574n=$((n+1))
575echo_i "checking that dom6.example. is no longer served by secondary ($n)"
576ret=0
577wait_for_no_soa @10.53.0.2 dom6.example. dig.out.test$n || ret=1
578if [ $ret -ne 0 ]; then echo_i "failed"; fi
579status=$((status+ret))
580
581nextpart ns2/named.run >/dev/null
582
583n=$((n+1))
584echo_i "adding dom6.example. and an invalid global masters option (TSIG without IP) ($n)"
585ret=0
586$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
587    server 10.53.0.1 ${PORT}
588    update add label1.masters.catalog1.example. 3600 IN TXT "tsig_key"
589    update add 4346f565b4d63ddb99e5d2497ff22d04e878e8f8.zones.catalog1.example. 3600 IN PTR dom6.example.
590    send
591END
592if [ $ret -ne 0 ]; then echo_i "failed"; fi
593status=$((status+ret))
594
595n=$((n+1))
596echo_i "waiting for secondary to sync up ($n)"
597ret=0
598wait_for_message ns2/named.run  "catz: adding zone 'dom6.example' from catalog 'catalog1.example'" &&
599wait_for_message ns2/named.run  "error \"failure\" while trying to generate config for zone \"dom6.example\"" || ret=1
600if [ $ret -ne 0 ]; then echo_i "failed"; fi
601status=$((status+ret))
602
603n=$((n+1))
604echo_i "removing dom6.example. ($n)"
605ret=0
606$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
607    server 10.53.0.1 ${PORT}
608    update delete label1.masters.catalog1.example. 3600 IN TXT "tsig_key"
609    update delete 4346f565b4d63ddb99e5d2497ff22d04e878e8f8.zones.catalog1.example. 3600 IN PTR dom6.example.
610    send
611END
612if [ $ret -ne 0 ]; then echo_i "failed"; fi
613status=$((status+ret))
614
615n=$((n+1))
616echo_i "waiting for secondary to sync up ($n)"
617ret=0
618wait_for_message ns2/named.run  "catz: deleting zone 'dom6.example' from catalog 'catalog1.example' - success" > /dev/null || ret=1
619if [ $ret -ne 0 ]; then echo_i "failed"; fi
620status=$((status+ret))
621
622##########################################################################
623n=$((n+1))
624echo_i "Checking that a missing zone directory forces in-memory ($n)"
625ret=0
626grep "'nonexistent' not found; zone files will not be saved" ns2/named.run > /dev/null || ret=1
627if [ $ret -ne 0 ]; then echo_i "failed"; fi
628status=$((status+ret))
629
630##########################################################################
631echo_i "Testing allow-query and allow-transfer ACLs"
632n=$((n+1))
633echo_i "adding domains dom7.example. and dom8.example. to primary via RNDC ($n)"
634ret=0
635echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom7.example.db
636echo "@ IN NS invalid." >> ns1/dom7.example.db
637rndccmd 10.53.0.1 addzone dom7.example. '{type primary; file "dom7.example.db";};' || ret=1
638if [ $ret -ne 0 ]; then echo_i "failed"; fi
639status=$((status+ret))
640echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom8.example.db
641echo "@ IN NS invalid." >> ns1/dom8.example.db
642rndccmd 10.53.0.1 addzone dom8.example. '{type primary; file "dom8.example.db";};' || ret=1
643if [ $ret -ne 0 ]; then echo_i "failed"; fi
644status=$((status+ret))
645
646n=$((n+1))
647echo_i "checking that dom7.example. is now served by primary ($n)"
648ret=0
649wait_for_soa @10.53.0.1 dom7.example. dig.out.test$n || ret=1
650if [ $ret -ne 0 ]; then echo_i "failed"; fi
651status=$((status+ret))
652
653nextpart ns2/named.run >/dev/null
654
655n=$((n+1))
656echo_i "adding domain dom7.example. to catalog1 zone with an allow-query statement ($n)"
657ret=0
658$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
659    server 10.53.0.1 ${PORT}
660    update add 78833ec3c0059fd4540fee81c7eaddce088e7cd7.zones.catalog1.example. 3600 IN PTR dom7.example.
661    update add allow-query.78833ec3c0059fd4540fee81c7eaddce088e7cd7.zones.catalog1.example. 3600 IN APL 1:10.53.0.1/32 !1:10.53.0.0/30 1:0.0.0.0/0
662    send
663END
664if [ $ret -ne 0 ]; then echo_i "failed"; fi
665status=$((status+ret))
666
667n=$((n+1))
668echo_i "waiting for secondary to sync up ($n)"
669ret=0
670wait_for_message ns2/named.run  "catz: adding zone 'dom7.example' from catalog 'catalog1.example'" > /dev/null &&
671wait_for_message ns2/named.run  "transfer of 'dom7.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
672if [ $ret -ne 0 ]; then echo_i "failed"; fi
673status=$((status+ret))
674
675n=$((n+1))
676echo_i "checking that dom7.example. is accessible from 10.53.0.1 ($n)"
677ret=0
678wait_for_soa @10.53.0.2 dom7.example. dig.out.test$n -b 10.53.0.1 || ret=1
679if [ $ret -ne 0 ]; then echo_i "failed"; fi
680status=$((status+ret))
681
682n=$((n+1))
683echo_i "checking that dom7.example. is not accessible from 10.53.0.2 ($n)"
684ret=0
685wait_for_no_soa @10.53.0.2 dom7.example. dig.out.test$n -b 10.53.0.2 || ret=1
686if [ $ret -ne 0 ]; then echo_i "failed"; fi
687status=$((status+ret))
688
689n=$((n+1))
690echo_i "checking that dom7.example. is accessible from 10.53.0.5 ($n)"
691ret=0
692wait_for_soa @10.53.0.2 dom7.example. dig.out.test$n -b 10.53.0.5 || ret=1
693if [ $ret -ne 0 ]; then echo_i "failed"; fi
694status=$((status+ret))
695
696nextpart ns2/named.run >/dev/null
697n=$((n+1))
698echo_i "adding dom8.example. domain and global allow-query and allow-transfer ACLs ($n)"
699ret=0
700$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
701    server 10.53.0.1 ${PORT}
702    update add cba95222e308baba42417be6021026fdf20827b6.zones.catalog1.example. 3600 IN PTR dom8.example
703    update add allow-query.catalog1.example. 3600 IN APL 1:10.53.0.1/32
704    update add allow-transfer.catalog1.example. 3600 IN APL 1:10.53.0.2/32
705    send
706END
707if [ $ret -ne 0 ]; then echo_i "failed"; fi
708status=$((status+ret))
709
710n=$((n+1))
711echo_i "waiting for secondary to sync up ($n)"
712ret=0
713wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" &&
714wait_for_message ns2/named.run  "transfer of 'dom8.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
715if [ $ret -ne 0 ]; then echo_i "failed"; fi
716status=$((status+ret))
717
718n=$((n+1))
719echo_i "checking that dom8.example. is accessible from 10.53.0.1 ($n)"
720ret=0
721wait_for_soa @10.53.0.2 dom8.example. dig.out.test$n -b 10.53.0.1 || ret=1
722if [ $ret -ne 0 ]; then echo_i "failed"; fi
723status=$((status+ret))
724
725n=$((n+1))
726echo_i "checking that dom8.example. is not accessible from 10.53.0.2 ($n)"
727ret=0
728wait_for_no_soa @10.53.0.2 dom8.example. dig.out.test$n -b 10.53.0.2 || ret=1
729if [ $ret -ne 0 ]; then echo_i "failed"; fi
730status=$((status+ret))
731
732n=$((n+1))
733echo_i "checking that dom8.example. is not AXFR accessible from 10.53.0.1 ($n)"
734ret=0
735dig_with_opts @10.53.0.2 axfr dom8.example. -b 10.53.0.1 > dig.out.test$n
736grep "Transfer failed." dig.out.test$n > /dev/null || ret=1
737if [ $ret -ne 0 ]; then echo_i "failed"; fi
738status=$((status+ret))
739
740n=$((n+1))
741echo_i "checking that dom8.example. is AXFR accessible from 10.53.0.2 ($n)"
742ret=0
743dig_with_opts @10.53.0.2 axfr dom8.example. -b 10.53.0.2 > dig.out.test$n
744grep -v "Transfer failed." dig.out.test$n > /dev/null || ret=1
745if [ $ret -ne 0 ]; then echo_i "failed"; fi
746status=$((status+ret))
747
748nextpart ns2/named.run >/dev/null
749n=$((n+1))
750echo_i "deleting global allow-query and allow-domain ACLs ($n)"
751ret=0
752$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
753    server 10.53.0.1 ${PORT}
754    update delete allow-query.catalog1.example. 3600 IN APL 1:10.53.0.1/32
755    update delete allow-transfer.catalog1.example. 3600 IN APL 1:10.53.0.2/32
756    send
757END
758if [ $ret -ne 0 ]; then echo_i "failed"; fi
759status=$((status+ret))
760ret=0
761wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
762if [ $ret -ne 0 ]; then echo_i "failed"; fi
763status=$((status+ret))
764
765n=$((n+1))
766echo_i "checking that dom8.example. is accessible from 10.53.0.1 ($n)"
767ret=0
768wait_for_soa @10.53.0.2 dom8.example. dig.out.test$n -b 10.53.0.1 || ret=1
769if [ $ret -ne 0 ]; then echo_i "failed"; fi
770status=$((status+ret))
771
772n=$((n+1))
773echo_i "checking that dom8.example. is accessible from 10.53.0.2 ($n)"
774ret=0
775wait_for_soa @10.53.0.2 dom8.example. dig.out.test$n -b 10.53.0.2 || ret=1
776if [ $ret -ne 0 ]; then echo_i "failed"; fi
777status=$((status+ret))
778
779n=$((n+1))
780echo_i "checking that dom8.example. is AXFR accessible from 10.53.0.1 ($n)"
781ret=0
782dig_with_opts @10.53.0.2 axfr dom8.example. -b 10.53.0.1 > dig.out.test$n
783grep -v "Transfer failed." dig.out.test$n > /dev/null || ret=1
784if [ $ret -ne 0 ]; then echo_i "failed"; fi
785status=$((status+ret))
786
787n=$((n+1))
788echo_i "checking that dom8.example. is AXFR accessible from 10.53.0.2 ($n)"
789ret=0
790dig_with_opts @10.53.0.2 axfr dom8.example. -b 10.53.0.2 > dig.out.test$n
791grep -v "Transfer failed." dig.out.test$n > /dev/null || ret=1
792if [ $ret -ne 0 ]; then echo_i "failed"; fi
793status=$((status+ret))
794
795
796##########################################################################
797echo_i "Testing TSIG keys for masters set per-domain"
798n=$((n+1))
799echo_i "adding a domain dom9.example. to primary via RNDC, with transfers allowed only with TSIG key ($n)"
800ret=0
801echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom9.example.db
802echo "@ IN NS invalid." >> ns1/dom9.example.db
803rndccmd 10.53.0.1 addzone dom9.example. '{type primary; file "dom9.example.db"; allow-transfer { key tsig_key; }; };' || ret=1
804if [ $ret -ne 0 ]; then echo_i "failed"; fi
805status=$((status+ret))
806
807n=$((n+1))
808echo_i "checking that dom9.example. is now served by primary ($n)"
809ret=0
810wait_for_soa @10.53.0.1 dom9.example. dig.out.test$n || ret=1
811if [ $ret -ne 0 ]; then echo_i "failed"; fi
812status=$((status+ret))
813
814nextpart ns2/named.run >/dev/null
815
816n=$((n+1))
817echo_i "adding domain dom9.example. to catalog1 zone with a valid masters suboption (IP with TSIG) ($n)"
818ret=0
819$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
820    server 10.53.0.1 ${PORT}
821    update add f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN PTR dom9.example.
822    update add label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN A 10.53.0.1
823    update add label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN TXT "tsig_key"
824    send
825END
826if [ $ret -ne 0 ]; then echo_i "failed"; fi
827status=$((status+ret))
828
829n=$((n+1))
830echo_i "waiting for secondary to sync up ($n)"
831ret=0
832wait_for_message ns2/named.run  "catz: adding zone 'dom9.example' from catalog 'catalog1.example'" &&
833wait_for_message ns2/named.run  "transfer of 'dom9.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
834if [ $ret -ne 0 ]; then echo_i "failed"; fi
835status=$((status+ret))
836
837n=$((n+1))
838echo_i "checking that dom9.example. is accessible on secondary ($n)"
839ret=0
840wait_for_soa @10.53.0.2 dom9.example. dig.out.test$n || ret=1
841if [ $ret -ne 0 ]; then echo_i "failed"; fi
842status=$((status+ret))
843
844n=$((n+1))
845echo_i "change TSIG key name on primary ($n)"
846ret=0
847rndccmd 10.53.0.1 modzone dom9.example. '{type primary; notify yes; file "dom9.example.db"; allow-transfer { key next_key; }; };' || ret=1
848if [ $ret -ne 0 ]; then echo_i "failed"; fi
849status=$((status+ret))
850
851n=$((n+1))
852echo_i "update TSIG key name in catalog zone ($n)"
853ret=0
854$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
855    server 10.53.0.1 ${PORT}
856    update del label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN TXT "tsig_key"
857    update add label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN TXT "next_key"
858    send
859END
860if [ $ret -ne 0 ]; then echo_i "failed"; fi
861status=$((status+ret))
862
863n=$((n+1))
864echo_i "waiting for secondary to sync up ($n)"
865ret=0
866wait_for_message ns2/named.run  "catz: modifying zone 'dom9.example' from catalog 'catalog1.example'" || ret=1
867if [ $ret -ne 0 ]; then echo_i "failed"; fi
868status=$((status+ret))
869
870n=$((n+1))
871echo_i "update zone contents and reload ($n)"
872ret=0
873echo "@ 3600 IN SOA . . 2 3600 3600 3600 3600" > ns1/dom9.example.db
874echo "@ IN NS ns2" >> ns1/dom9.example.db
875echo "ns2 IN A 10.53.0.2" >> ns1/dom9.example.db
876rndccmd 10.53.0.1 reload dom9.example. || ret=1
877if [ $ret -ne 0 ]; then echo_i "failed"; fi
878status=$((status+ret))
879
880n=$((n+1))
881echo_i "wait for primary to update zone ($n)"
882ret=0
883wait_for_a @10.53.0.1 ns2.dom9.example. dig.out.test$n || ret=1
884if [ $ret -ne 0 ]; then echo_i "failed"; fi
885status=$((status+ret))
886
887n=$((n+1))
888echo_i "wait for secondary to update zone ($n)"
889ret=0
890wait_for_a @10.53.0.2 ns2.dom9.example. dig.out.test$n || ret=1
891if [ $ret -ne 0 ]; then echo_i "failed"; fi
892status=$((status+ret))
893
894n=$((n+1))
895echo_i "deleting domain dom9.example. from catalog1 zone ($n)"
896ret=0
897$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
898    server 10.53.0.1 ${PORT}
899    update delete f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN PTR dom9.example.
900    update delete label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN A 10.53.0.1
901    update delete label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN TXT "next_key"
902    send
903END
904if [ $ret -ne 0 ]; then echo_i "failed"; fi
905status=$((status+ret))
906
907n=$((n+1))
908echo_i "waiting for secondary to sync up ($n)"
909ret=0
910wait_for_message ns2/named.run  "catz: deleting zone 'dom9.example' from catalog 'catalog1.example' - success" || ret=1
911if [ $ret -ne 0 ]; then echo_i "failed"; fi
912status=$((status+ret))
913
914n=$((n+1))
915echo_i "checking that dom9.example. is no longer accessible on secondary ($n)"
916ret=0
917wait_for_no_soa @10.53.0.2 dom9.example. dig.out.test$n || ret=1
918if [ $ret -ne 0 ]; then echo_i "failed"; fi
919status=$((status+ret))
920
921nextpart ns2/named.run >/dev/null
922
923n=$((n+1))
924echo_i "adding domain dom9.example. to catalog1 zone with an invalid masters suboption (TSIG without IP) ($n)"
925ret=0
926$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
927    server 10.53.0.1 ${PORT}
928    update add f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN PTR dom9.example.
929    update add label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN TXT "tsig_key"
930    send
931END
932if [ $ret -ne 0 ]; then echo_i "failed"; fi
933status=$((status+ret))
934
935n=$((n+1))
936echo_i "waiting for secondary to sync up ($n)"
937ret=0
938wait_for_message ns2/named.run  "catz: adding zone 'dom9.example' from catalog 'catalog1.example'" &&
939wait_for_message ns2/named.run  "error \"failure\" while trying to generate config for zone \"dom9.example\"" || ret=1
940if [ $ret -ne 0 ]; then echo_i "failed"; fi
941status=$((status+ret))
942
943n=$((n+1))
944echo_i "deleting domain dom9.example. from catalog1 zone ($n)"
945ret=0
946$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
947    server 10.53.0.1 ${PORT}
948    update delete f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN PTR dom9.example.
949    update delete label1.masters.f0f989bc71c5c8ca3a1eb9c9ab5246521907e3af.zones.catalog1.example. 3600 IN TXT "tsig_key"
950    send
951END
952if [ $ret -ne 0 ]; then echo_i "failed"; fi
953status=$((status+ret))
954
955n=$((n+1))
956echo_i "waiting for secondary to sync up ($n)"
957ret=0
958wait_for_message ns2/named.run  "catz: deleting zone 'dom9.example' from catalog 'catalog1.example'" || ret=1
959if [ $ret -ne 0 ]; then echo_i "failed"; fi
960status=$((status+ret))
961
962##########################################################################
963echo_i "Testing catalog entries that can't be represented as filenames"
964# note: we need 4 backslashes in the shell to get 2 backslashes in DNS
965# presentation format, which is 1 backslash on the wire.
966for special in \
967       this.is.a.very.very.long.long.long.domain.that.will.cause.catalog.zones.to.generate.hash.instead.of.using.regular.filename.dom10.example \
968       this.zone/domain.has.a.slash.dom10.example \
969       this.zone\\\\domain.has.backslash.dom10.example \
970       this.zone:domain.has.a.colon.dom.10.example
971do
972    # hashes below are generated by:
973    # python ${TOP}/contrib/scripts/catzhash.py "${special}"
974
975    case "$special" in
976    this.is.a.very.very.long.long.long.domain.that.will.cause.catalog.zones.to.generate.hash.instead.of.using.regular.filename.dom10.example)
977        hash=825f48b1ce1b4cf5a041d20255a0c8e98d114858
978        db=__catz__4d70696f2335687069467f11f5d5378c480383f97782e553fb2d04a7bb2a23ed.db
979        ;;
980    this.zone/domain.has.a.slash.dom10.example)
981        hash=e64cc64c99bf52d0a77fb16dd7ed57cf925a36aa
982        db=__catz__46ba3e1b28d5955e5313d5fee61bedc78c71d08035aa7ea2f7bf0b8228ab3acc.db
983        ;;
984    this.zone\\\\domain.has.backslash.dom10.example)
985        hash=91e27e02153d38cf656a9b376d7747fbcd19f985
986        db=__catz__b667f7ff802c0895e0506699951cff9a1cab68c5ef8546aa0d07425f244ed870.db
987        ;;
988    this.zone:domain.has.a.colon.dom.10.example)
989        hash=8b7238bf4c34045834c573ba4116557ebb24d33c
990        db=__catz__5c721f7872913a4e7fa8ad42589cce5dd6e551a4c9e6ab3f86e77c0bbc7c2ca6.db
991        ;;
992    esac
993
994    n=$((n+1))
995    echo_i "checking that ${special}. is not served by primary ($n)"
996    ret=0
997    wait_for_no_soa @10.53.0.1 "${special}" dig.out.test$n || ret=1
998    if [ $ret -ne 0 ]; then echo_i "failed"; fi
999    status=$((status+ret))
1000
1001    n=$((n+1))
1002    echo_i "Adding a domain ${special}. to primary via RNDC ($n)"
1003    ret=0
1004    echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom10.example.db
1005    echo "@ IN NS invalid." >> ns1/dom10.example.db
1006    rndccmd 10.53.0.1 addzone '"'"${special}"'"' '{type primary; file "dom10.example.db";};' || ret=1
1007    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1008    status=$((status+ret))
1009
1010    n=$((n+1))
1011    echo_i "checking that ${special}. is now served by primary ($n)"
1012    ret=0
1013    wait_for_soa @10.53.0.1 "${special}." dig.out.test$n || ret=1
1014    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1015    status=$((status+ret))
1016
1017    nextpart ns2/named.run >/dev/null
1018
1019    n=$((n+1))
1020    echo_i "Adding domain ${special}. to catalog1 zone ($n)"
1021    ret=0
1022    $NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1023      server 10.53.0.1 ${PORT}
1024      update add ${hash}.zones.catalog1.example 3600 IN PTR ${special}.
1025      send
1026END
1027    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1028    status=$((status+ret))
1029
1030    n=$((n+1))
1031    echo_i "waiting for secondary to sync up ($n)"
1032    ret=0
1033    wait_for_message ns2/named.run  "catz: adding zone '$special' from catalog 'catalog1.example'" &&
1034    wait_for_message ns2/named.run  "transfer of '$special/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1035    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1036    status=$((status+ret))
1037
1038    n=$((n+1))
1039    echo_i "checking that ${special}. is served by secondary ($n)"
1040    ret=0
1041    wait_for_soa @10.53.0.2 "${special}." dig.out.test$n || ret=1
1042    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1043    status=$((status+ret))
1044
1045    n=$((n+1))
1046    echo_i "checking that zone-directory is populated with a hashed filename ($n)"
1047    ret=0
1048    wait_for_zonefile "ns2/zonedir/$db" || ret=1
1049    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1050    status=$((status+ret))
1051
1052    n=$((n+1))
1053    echo_i "removing domain ${special}. from catalog1 zone ($n)"
1054    ret=0
1055    $NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1056      server 10.53.0.1 ${PORT}
1057      update delete ${hash}.zones.catalog1.example
1058      send
1059END
1060    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1061    status=$((status+ret))
1062
1063    n=$((n+1))
1064    echo_i "waiting for secondary to sync up ($n)"
1065    ret=0
1066    wait_for_message ns2/named.run  "zone_shutdown: zone ${special}/IN: shutting down" || ret=1
1067    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1068    status=$((status+ret))
1069
1070    n=$((n+1))
1071    echo_i "checking that ${special}. is not served by secondary ($n)"
1072    ret=0
1073    wait_for_no_soa @10.53.0.2 "${special}." dig.out.test$n || ret=1
1074    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1075    status=$((status+ret))
1076
1077    n=$((n+1))
1078    echo_i "checking that zone-directory is emptied ($n)"
1079    ret=0
1080    wait_for_no_zonefile "ns2/zonedir/$db" || ret=1
1081    wait_for_no_zonefile "ns2/zonedir/$db.jnl" || ret=1
1082    if [ $ret -ne 0 ]; then echo_i "failed"; fi
1083    status=$((status+ret))
1084done
1085
1086##########################################################################
1087echo_i "Testing adding a domain and a subdomain of it"
1088n=$((n+1))
1089echo_i "checking that dom11.example. is not served by primary ($n)"
1090ret=0
1091wait_for_no_soa @10.53.0.1 dom11.example. dig.out.test$n || ret=1
1092if [ $ret -ne 0 ]; then echo_i "failed"; fi
1093status=$((status+ret))
1094
1095n=$((n+1))
1096echo_i "Adding a domain dom11.example. to primary via RNDC ($n)"
1097ret=0
1098echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom11.example.db
1099echo "@ IN NS invalid." >> ns1/dom11.example.db
1100rndccmd 10.53.0.1 addzone dom11.example. '{type primary; file "dom11.example.db";};' || ret=1
1101if [ $ret -ne 0 ]; then echo_i "failed"; fi
1102status=$((status+ret))
1103
1104n=$((n+1))
1105echo_i "checking that dom11.example. is now served by primary ($n)"
1106ret=0
1107wait_for_soa @10.53.0.1 dom11.example. dig.out.test$n || ret=1
1108if [ $ret -ne 0 ]; then echo_i "failed"; fi
1109status=$((status+ret))
1110
1111nextpart ns2/named.run >/dev/null
1112
1113n=$((n+1))
1114echo_i "Adding domain dom11.example. to catalog1 zone ($n)"
1115ret=0
1116$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1117    server 10.53.0.1 ${PORT}
1118    update add 0580d70e769c86c8b951a488d8b776627f427d7a.zones.catalog1.example. 3600 IN PTR dom11.example.
1119    send
1120END
1121if [ $ret -ne 0 ]; then echo_i "failed"; fi
1122status=$((status+ret))
1123
1124n=$((n+1))
1125echo_i "waiting for secondary to sync up ($n)"
1126ret=0
1127wait_for_message ns2/named.run  "catz: adding zone 'dom11.example' from catalog 'catalog1.example'" &&
1128wait_for_message ns2/named.run  "transfer of 'dom11.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1129if [ $ret -ne 0 ]; then echo_i "failed"; fi
1130status=$((status+ret))
1131
1132n=$((n+1))
1133echo_i "checking that dom11.example. is served by secondary ($n)"
1134ret=0
1135wait_for_soa @10.53.0.2 dom11.example. dig.out.test$n || ret=1
1136if [ $ret -ne 0 ]; then echo_i "failed"; fi
1137status=$((status+ret))
1138
1139n=$((n+1))
1140echo_i "checking that subdomain.of.dom11.example. is not served by primary ($n)"
1141ret=0
1142wait_for_rcode NXDOMAIN SOA @10.53.0.1 subdomain.of.dom11.example. dig.out.test$n || ret=1
1143if [ $ret -ne 0 ]; then echo_i "failed"; fi
1144status=$((status+ret))
1145
1146n=$((n+1))
1147echo_i "Adding a domain subdomain.of.dom11.example. to primary via RNDC ($n)"
1148ret=0
1149echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/subdomain.of.dom11.example.db
1150echo "@ IN NS invalid." >> ns1/subdomain.of.dom11.example.db
1151rndccmd 10.53.0.1 addzone subdomain.of.dom11.example. '{type primary; file "subdomain.of.dom11.example.db";};' || ret=1
1152if [ $ret -ne 0 ]; then echo_i "failed"; fi
1153status=$((status+ret))
1154
1155n=$((n+1))
1156echo_i "checking that subdomain.of.dom11.example. is now served by primary ($n)"
1157ret=0
1158wait_for_soa @10.53.0.1 subdomain.of.dom11.example. dig.out.test$n || ret=1
1159if [ $ret -ne 0 ]; then echo_i "failed"; fi
1160status=$((status+ret))
1161
1162nextpart ns2/named.run >/dev/null
1163
1164n=$((n+1))
1165echo_i "Adding domain subdomain.of.dom11.example. to catalog1 zone ($n)"
1166ret=0
1167$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1168    server 10.53.0.1 ${PORT}
1169    update add 25557e0bdd10cb3710199bb421b776df160f241e.zones.catalog1.example. 3600 IN PTR subdomain.of.dom11.example.
1170    send
1171END
1172if [ $ret -ne 0 ]; then echo_i "failed"; fi
1173status=$((status+ret))
1174
1175n=$((n+1))
1176echo_i "waiting for secondary to sync up ($n)"
1177ret=0
1178wait_for_message ns2/named.run  "catz: adding zone 'subdomain.of.dom11.example' from catalog 'catalog1.example'" &&
1179wait_for_message ns2/named.run  "transfer of 'subdomain.of.dom11.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1180if [ $ret -ne 0 ]; then echo_i "failed"; fi
1181status=$((status+ret))
1182
1183n=$((n+1))
1184echo_i "checking that subdomain.of.dom11.example. is served by secondary ($n)"
1185ret=0
1186wait_for_soa @10.53.0.2 subdomain.of.dom11.example. dig.out.test$n || ret=1
1187if [ $ret -ne 0 ]; then echo_i "failed"; fi
1188status=$((status+ret))
1189
1190n=$((n+1))
1191echo_i "removing domain dom11.example. from catalog1 zone ($n)"
1192ret=0
1193$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1194   server 10.53.0.1 ${PORT}
1195   update delete 0580d70e769c86c8b951a488d8b776627f427d7a.zones.catalog1.example
1196   send
1197END
1198if [ $ret -ne 0 ]; then echo_i "failed"; fi
1199status=$((status+ret))
1200
1201n=$((n+1))
1202echo_i "waiting for secondary to sync up ($n)"
1203ret=0
1204wait_for_message ns2/named.run  "zone_shutdown: zone dom11.example/IN: shutting down" || ret=1
1205if [ $ret -ne 0 ]; then echo_i "failed"; fi
1206status=$((status+ret))
1207
1208n=$((n+1))
1209echo_i "checking that dom11.example. is not served by secondary ($n)"
1210ret=0
1211wait_for_no_soa @10.53.0.2 dom11.example. dig.out.test$n || ret=1
1212if [ $ret -ne 0 ]; then echo_i "failed"; fi
1213status=$((status+ret))
1214
1215n=$((n+1))
1216echo_i "checking that subdomain.of.dom11.example. is still served by secondary ($n)"
1217ret=0
1218wait_for_soa @10.53.0.2 subdomain.of.dom11.example. dig.out.test$n || ret=1
1219if [ $ret -ne 0 ]; then echo_i "failed"; fi
1220status=$((status+ret))
1221
1222n=$((n+1))
1223echo_i "removing domain subdomain.of.dom11.example. from catalog1 zone ($n)"
1224ret=0
1225$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1226   server 10.53.0.1 ${PORT}
1227   update delete 25557e0bdd10cb3710199bb421b776df160f241e.zones.catalog1.example
1228   send
1229END
1230if [ $ret -ne 0 ]; then echo_i "failed"; fi
1231status=$((status+ret))
1232
1233n=$((n+1))
1234echo_i "waiting for secondary to sync up ($n)"
1235ret=0
1236wait_for_message ns2/named.run  "zone_shutdown: zone subdomain.of.dom11.example/IN: shutting down" || ret=1
1237if [ $ret -ne 0 ]; then echo_i "failed"; fi
1238status=$((status+ret))
1239
1240n=$((n+1))
1241echo_i "checking that subdomain.of.dom11.example. is not served by secondary ($n)"
1242ret=0
1243wait_for_no_soa @10.53.0.2 subdomain.of.d11.example. dig.out.test$n || ret=1
1244if [ $ret -ne 0 ]; then echo_i "failed"; fi
1245status=$((status+ret))
1246
1247##########################################################################
1248echo_i "Testing adding a catalog zone at runtime with rndc reconfig"
1249n=$((n+1))
1250echo_i "checking that dom12.example. is not served by primary ($n)"
1251ret=0
1252wait_for_no_soa @10.53.0.1 dom12.example. dig.out.test$n || ret=1
1253if [ $ret -ne 0 ]; then echo_i "failed"; fi
1254status=$((status+ret))
1255
1256n=$((n+1))
1257echo_i "Adding a domain dom12.example. to primary via RNDC ($n)"
1258ret=0
1259echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom12.example.db
1260echo "@ IN NS invalid." >> ns1/dom12.example.db
1261rndccmd 10.53.0.1 addzone dom12.example. '{type primary; file "dom12.example.db";};' || ret=1
1262if [ $ret -ne 0 ]; then echo_i "failed"; fi
1263status=$((status+ret))
1264
1265n=$((n+1))
1266echo_i "checking that dom12.example. is now served by primary ($n)"
1267ret=0
1268wait_for_soa @10.53.0.1 dom12.example. dig.out.test$n || ret=1
1269if [ $ret -ne 0 ]; then echo_i "failed"; fi
1270status=$((status+ret))
1271
1272nextpart ns2/named.run >/dev/null
1273
1274n=$((n+1))
1275echo_i "Adding domain dom12.example. to catalog4 zone ($n)"
1276ret=0
1277$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1278    server 10.53.0.1 ${PORT}
1279    update add 871d51e5433543c0f6fb263c40f359fbc152c8ae.zones.catalog4.example. 3600 IN PTR dom12.example.
1280    send
1281END
1282if [ $ret -ne 0 ]; then echo_i "failed"; fi
1283status=$((status+ret))
1284
1285n=$((n+1))
1286echo_i "checking that dom12.example. is not served by secondary ($n)"
1287ret=0
1288wait_for_no_soa @10.53.0.2 dom12.example. dig.out.test$n || ret=1
1289if [ $ret -ne 0 ]; then echo_i "failed"; fi
1290status=$((status+ret))
1291
1292
1293n=$((n+1))
1294echo_i "reconfiguring secondary - adding catalog4 catalog zone ($n)"
1295ret=0
1296sed -e "s/^#T1//g" <  ns2/named1.conf.in > ns2/named.conf.tmp
1297copy_setports ns2/named.conf.tmp ns2/named.conf
1298rndccmd 10.53.0.2 reconfig || ret=1
1299if [ $ret -ne 0 ]; then echo_i "failed"; fi
1300status=$((status+ret))
1301
1302n=$((n+1))
1303echo_i "waiting for secondary to sync up ($n)"
1304ret=0
1305wait_for_message ns2/named.run  "catz: adding zone 'dom12.example' from catalog 'catalog4.example'" &&
1306wait_for_message ns2/named.run  "transfer of 'dom12.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1307if [ $ret -ne 0 ]; then echo_i "failed"; fi
1308status=$((status+ret))
1309
1310n=$((n+1))
1311echo_i "checking that dom7.example. is still served by secondary after reconfiguration ($n)"
1312ret=0
1313wait_for_soa @10.53.0.2 dom7.example. dig.out.test$n -b 10.53.0.1 || ret=1
1314if [ $ret -ne 0 ]; then echo_i "failed"; fi
1315status=$((status+ret))
1316n=$((n+1))
1317
1318echo_i "checking that dom12.example. is served by secondary ($n)"
1319ret=0
1320wait_for_soa @10.53.0.2 dom12.example. dig.out.test$n || ret=1
1321if [ $ret -ne 0 ]; then echo_i "failed"; fi
1322status=$((status+ret))
1323
1324n=$((n+1))
1325echo_i "reconfiguring secondary - removing catalog4 catalog zone, adding non-existent catalog5 catalog zone ($n)"
1326ret=0
1327sed -e "s/^#T2//" < ns2/named1.conf.in > ns2/named.conf.tmp
1328copy_setports ns2/named.conf.tmp ns2/named.conf
1329$RNDC -c ../common/rndc.conf -s 10.53.0.2 -p "${CONTROLPORT}" reconfig > /dev/null 2>&1 && ret=1
1330if [ $ret -ne 0 ]; then echo_i "failed"; fi
1331status=$((status+ret))
1332
1333n=$((n+1))
1334echo_i "reconfiguring secondary - removing non-existent catalog5 catalog zone ($n)"
1335ret=0
1336copy_setports ns2/named1.conf.in ns2/named.conf
1337rndccmd 10.53.0.2 reconfig || ret=1
1338if [ $ret -ne 0 ]; then echo_i "failed"; fi
1339status=$((status+ret))
1340
1341n=$((n+1))
1342echo_i "checking that dom12.example. is not served by secondary ($n)"
1343ret=0
1344wait_for_no_soa @10.53.0.2 dom12.example. dig.out.test$n || ret=1
1345if [ $ret -ne 0 ]; then echo_i "failed"; fi
1346status=$((status+ret))
1347
1348n=$((n+1))
1349echo_i "removing domain dom12.example. from catalog4 zone ($n)"
1350ret=0
1351$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1352    server 10.53.0.1 ${PORT}
1353    update delete 871d51e5433543c0f6fb263c40f359fbc152c8ae.zones.catalog4.example. 3600 IN PTR dom12.example.
1354    send
1355END
1356if [ $ret -ne 0 ]; then echo_i "failed"; fi
1357status=$((status+ret))
1358
1359##########################################################################
1360echo_i "Testing having a zone in two different catalogs"
1361n=$((n+1))
1362echo_i "checking that dom13.example. is not served by primary ($n)"
1363ret=0
1364wait_for_no_soa @10.53.0.1 dom13.example. dig.out.test$n || ret=1
1365if [ $ret -ne 0 ]; then echo_i "failed"; fi
1366status=$((status+ret))
1367
1368n=$((n+1))
1369echo_i "Adding a domain dom13.example. to primary ns1 via RNDC ($n)"
1370ret=0
1371echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom13.example.db
1372echo "@ IN NS invalid." >> ns1/dom13.example.db
1373echo "@ IN A 192.0.2.1" >> ns1/dom13.example.db
1374rndccmd 10.53.0.1 addzone dom13.example. '{type primary; file "dom13.example.db";};' || ret=1
1375if [ $ret -ne 0 ]; then echo_i "failed"; fi
1376status=$((status+ret))
1377
1378n=$((n+1))
1379echo_i "checking that dom13.example. is now served by primary ns1 ($n)"
1380ret=0
1381wait_for_soa @10.53.0.1 dom13.example. dig.out.test$n || ret=1
1382if [ $ret -ne 0 ]; then echo_i "failed"; fi
1383status=$((status+ret))
1384
1385n=$((n+1))
1386echo_i "Adding a domain dom13.example. to primary ns3 via RNDC ($n)"
1387ret=0
1388echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns3/dom13.example.db
1389echo "@ IN NS invalid." >> ns3/dom13.example.db
1390echo "@ IN A 192.0.2.2" >> ns3/dom13.example.db
1391rndccmd 10.53.0.3 addzone dom13.example. '{type primary; file "dom13.example.db";};' || ret=1
1392if [ $ret -ne 0 ]; then echo_i "failed"; fi
1393status=$((status+ret))
1394
1395n=$((n+1))
1396echo_i "checking that dom13.example. is now served by primary ns3 ($n)"
1397ret=0
1398wait_for_soa @10.53.0.3 dom13.example. dig.out.test$n || ret=1
1399if [ $ret -ne 0 ]; then echo_i "failed"; fi
1400status=$((status+ret))
1401
1402
1403nextpart ns2/named.run >/dev/null
1404
1405n=$((n+1))
1406echo_i "Adding domain dom13.example. to catalog1 zone with ns1 as primary ($n)"
1407ret=0
1408$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1409    server 10.53.0.1 ${PORT}
1410    update add 8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog1.example. 3600 IN PTR dom13.example.
1411    update add masters.8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog1.example. 3600 IN A 10.53.0.1
1412    send
1413END
1414if [ $ret -ne 0 ]; then echo_i "failed"; fi
1415status=$((status+ret))
1416
1417n=$((n+1))
1418echo_i "waiting for secondary to sync up ($n)"
1419ret=0
1420wait_for_message ns2/named.run  "catz: adding zone 'dom13.example' from catalog 'catalog1.example'" &&
1421wait_for_message ns2/named.run  "transfer of 'dom13.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1422if [ $ret -ne 0 ]; then echo_i "failed"; fi
1423status=$((status+ret))
1424
1425nextpart ns2/named.run >/dev/null
1426
1427n=$((n+1))
1428echo_i "checking that dom13.example. is served by secondary and that it's the one from ns1 ($n)"
1429ret=0
1430wait_for_a @10.53.0.2 dom13.example. dig.out.test$n || ret=1
1431grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1432if [ $ret -ne 0 ]; then echo_i "failed"; fi
1433status=$((status+ret))
1434
1435n=$((n+1))
1436echo_i "Adding domain dom13.example. to catalog2 zone with ns3 as primary ($n)"
1437ret=0
1438$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1439    server 10.53.0.3 ${PORT}
1440    update add 8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog2.example. 3600 IN PTR dom13.example.
1441    update add masters.8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog2.example. 3600 IN A 10.53.0.3
1442    send
1443END
1444if [ $ret -ne 0 ]; then echo_i "failed"; fi
1445status=$((status+ret))
1446
1447n=$((n+1))
1448echo_i "waiting for secondary to sync up ($n)"
1449ret=0
1450wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1451if [ $ret -ne 0 ]; then echo_i "failed"; fi
1452status=$((status+ret))
1453
1454n=$((n+1))
1455echo_i "checking that dom13.example. is served by secondary and that it's still the one from ns1 ($n)"
1456ret=0
1457wait_for_a @10.53.0.2 dom13.example. dig.out.test$n || ret=1
1458grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1459if [ $ret -ne 0 ]; then echo_i "failed"; fi
1460status=$((status+ret))
1461
1462nextpart ns2/named.run >/dev/null
1463
1464n=$((n+1))
1465echo_i "Deleting domain dom13.example. from catalog2 ($n)"
1466ret=0
1467$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1468    server 10.53.0.3 ${PORT}
1469    update delete 8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog2.example. 3600 IN PTR dom13.example.
1470    update delete masters.8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog2.example. 3600 IN A 10.53.0.3
1471    send
1472END
1473if [ $ret -ne 0 ]; then echo_i "failed"; fi
1474status=$((status+ret))
1475
1476n=$((n+1))
1477echo_i "waiting for secondary to sync up ($n)"
1478ret=0
1479wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1480if [ $ret -ne 0 ]; then echo_i "failed"; fi
1481status=$((status+ret))
1482
1483n=$((n+1))
1484echo_i "checking that dom13.example. is served by secondary and that it's still the one from ns1 ($n)"
1485ret=0
1486wait_for_a @10.53.0.2 dom13.example. dig.out.test$n || ret=1
1487grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1488if [ $ret -ne 0 ]; then echo_i "failed"; fi
1489status=$((status+ret))
1490
1491n=$((n+1))
1492echo_i "Deleting domain dom13.example. from catalog1 ($n)"
1493ret=0
1494$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1495    server 10.53.0.1 ${PORT}
1496    update delete 8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog1.example. 3600 IN PTR dom13.example.
1497    update delete masters.8d7989c746b3f92b3bba2479e72afd977198363f.zones.catalog1.example. 3600 IN A 10.53.0.2
1498    send
1499END
1500if [ $ret -ne 0 ]; then echo_i "failed"; fi
1501status=$((status+ret))
1502
1503n=$((n+1))
1504echo_i "waiting for secondary to sync up ($n)"
1505ret=0
1506wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1507if [ $ret -ne 0 ]; then echo_i "failed"; fi
1508status=$((status+ret))
1509
1510n=$((n+1))
1511echo_i "checking that dom13.example. is no longer served by secondary ($n)"
1512ret=0
1513wait_for_no_soa @10.53.0.2 dom13.example. dig.out.test$n || ret=1
1514if [ $ret -ne 0 ]; then echo_i "failed"; fi
1515status=$((status+ret))
1516
1517##########################################################################
1518echo_i "Testing having a regular zone and a zone in catalog zone of the same name"
1519n=$((n+1))
1520echo_i "checking that dom14.example. is not served by primary ($n)"
1521ret=0
1522wait_for_no_soa @10.53.0.1 dom14.example. dig.out.test$n || ret=1
1523if [ $ret -ne 0 ]; then echo_i "failed"; fi
1524status=$((status+ret))
1525
1526n=$((n+1))
1527echo_i "Adding a domain dom14.example. to primary ns1 via RNDC ($n)"
1528ret=0
1529echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom14.example.db
1530echo "@ IN NS invalid." >> ns1/dom14.example.db
1531echo "@ IN A 192.0.2.1" >> ns1/dom14.example.db
1532rndccmd 10.53.0.1 addzone dom14.example. '{type primary; file "dom14.example.db";};' || ret=1
1533if [ $ret -ne 0 ]; then echo_i "failed"; fi
1534status=$((status+ret))
1535
1536n=$((n+1))
1537echo_i "checking that dom14.example. is now served by primary ns1 ($n)"
1538ret=0
1539wait_for_soa @10.53.0.1 dom14.example. dig.out.test$n || ret=1
1540if [ $ret -ne 0 ]; then echo_i "failed"; fi
1541status=$((status+ret))
1542
1543n=$((n+1))
1544echo_i "Adding a domain dom14.example. to primary ns3 via RNDC ($n)"
1545ret=0
1546echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns3/dom14.example.db
1547echo "@ IN NS invalid." >> ns3/dom14.example.db
1548echo "@ IN A 192.0.2.2" >> ns3/dom14.example.db
1549rndccmd 10.53.0.3 addzone dom14.example. '{type primary; file "dom14.example.db";};' || ret=1
1550if [ $ret -ne 0 ]; then echo_i "failed"; fi
1551status=$((status+ret))
1552
1553n=$((n+1))
1554echo_i "checking that dom14.example. is now served by primary ns3 ($n)"
1555ret=0
1556wait_for_soa @10.53.0.3 dom14.example. dig.out.test$n || ret=1
1557if [ $ret -ne 0 ]; then echo_i "failed"; fi
1558status=$((status+ret))
1559
1560nextpart ns2/named.run >/dev/null
1561
1562n=$((n+1))
1563echo_i "Adding domain dom14.example. with rndc with ns1 as primary ($n)"
1564ret=0
1565rndccmd 10.53.0.2 addzone dom14.example. '{type secondary; primaries {10.53.0.1;};};' || ret=1
1566if [ $ret -ne 0 ]; then echo_i "failed"; fi
1567status=$((status+ret))
1568
1569n=$((n+1))
1570echo_i "waiting for secondary to sync up ($n)"
1571ret=0
1572wait_for_message ns2/named.run  "transfer of 'dom14.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1573if [ $ret -ne 0 ]; then echo_i "failed"; fi
1574status=$((status+ret))
1575
1576nextpart ns2/named.run >/dev/null
1577
1578n=$((n+1))
1579echo_i "checking that dom14.example. is served by secondary and that it's the one from ns1 ($n)"
1580ret=0
1581wait_for_a @10.53.0.2 dom14.example. dig.out.test$n || ret=1
1582grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1583if [ $ret -ne 0 ]; then echo_i "failed"; fi
1584status=$((status+ret))
1585
1586n=$((n+1))
1587echo_i "Adding domain dom14.example. to catalog2 zone with ns3 as primary ($n)"
1588ret=0
1589$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1590    server 10.53.0.3 ${PORT}
1591    update add 45e3d45ea5f7bd01c395ccbde6ae2e750a3ee8ab.zones.catalog2.example. 3600 IN PTR dom14.example.
1592    update add masters.45e3d45ea5f7bd01c395ccbde6ae2e750a3ee8ab.zones.catalog2.example. 3600 IN A 10.53.0.3
1593    send
1594END
1595if [ $ret -ne 0 ]; then echo_i "failed"; fi
1596status=$((status+ret))
1597
1598n=$((n+1))
1599echo_i "waiting for secondary to sync up ($n)"
1600ret=0
1601wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1602if [ $ret -ne 0 ]; then echo_i "failed"; fi
1603status=$((status+ret))
1604
1605n=$((n+1))
1606echo_i "checking that dom14.example. is served by secondary and that it's still the one from ns1 ($n)"
1607ret=0
1608wait_for_a @10.53.0.2 dom14.example. dig.out.test$n || ret=1
1609grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1610if [ $ret -ne 0 ]; then echo_i "failed"; fi
1611status=$((status+ret))
1612
1613nextpart ns2/named.run >/dev/null
1614
1615n=$((n+1))
1616echo_i "Deleting domain dom14.example. from catalog2 ($n)"
1617ret=0
1618$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1619    server 10.53.0.3 ${PORT}
1620    update delete 45e3d45ea5f7bd01c395ccbde6ae2e750a3ee8ab.zones.catalog2.example. 3600 IN PTR dom14.example.
1621    update delete masters.45e3d45ea5f7bd01c395ccbde6ae2e750a3ee8ab.zones.catalog2.example. 3600 IN A 10.53.0.3
1622    send
1623END
1624if [ $ret -ne 0 ]; then echo_i "failed"; fi
1625status=$((status+ret))
1626
1627n=$((n+1))
1628echo_i "waiting for secondary to sync up ($n)"
1629ret=0
1630wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1631if [ $ret -ne 0 ]; then echo_i "failed"; fi
1632status=$((status+ret))
1633
1634n=$((n+1))
1635echo_i "checking that dom14.example. is served by secondary and that it's still the one from ns1 ($n)"
1636ret=0
1637wait_for_a @10.53.0.2 dom14.example. dig.out.test$n || ret=1
1638grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1639if [ $ret -ne 0 ]; then echo_i "failed"; fi
1640status=$((status+ret))
1641
1642##########################################################################
1643echo_i "Testing changing label for a member zone"
1644n=$((n+1))
1645echo_i "checking that dom15.example. is not served by primary ($n)"
1646ret=0
1647wait_for_no_soa @10.53.0.1 dom15.example. dig.out.test$n || ret=1
1648if [ $ret -ne 0 ]; then echo_i "failed"; fi
1649status=$((status+ret))
1650
1651n=$((n+1))
1652echo_i "Adding a domain dom15.example. to primary ns1 via RNDC ($n)"
1653ret=0
1654echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom15.example.db
1655echo "@ IN NS invalid." >> ns1/dom15.example.db
1656rndccmd 10.53.0.1 addzone dom15.example. '{type primary; file "dom15.example.db";};' || ret=1
1657if [ $ret -ne 0 ]; then echo_i "failed"; fi
1658status=$((status+ret))
1659
1660n=$((n+1))
1661echo_i "checking that dom15.example. is now served by primary ns1 ($n)"
1662ret=0
1663wait_for_soa @10.53.0.1 dom15.example. dig.out.test$n || ret=1
1664if [ $ret -ne 0 ]; then echo_i "failed"; fi
1665status=$((status+ret))
1666
1667nextpart ns2/named.run >/dev/null
1668
1669echo_i "Adding domain dom15.example. to catalog1 zone with 'dom15label1' label ($n)"
1670ret=0
1671$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1672    server 10.53.0.1 ${PORT}
1673    update add dom15label1.zones.catalog1.example. 3600 IN PTR dom15.example.
1674    send
1675END
1676if [ $ret -ne 0 ]; then echo_i "failed"; fi
1677status=$((status+ret))
1678
1679n=$((n+1))
1680echo_i "waiting for secondary to sync up ($n)"
1681ret=0
1682wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1683if [ $ret -ne 0 ]; then echo_i "failed"; fi
1684status=$((status+ret))
1685
1686sleep 3
1687
1688n=$((n+1))
1689echo_i "checking that dom15.example. is served by secondary ($n)"
1690ret=0
1691wait_for_soa @10.53.0.2 dom15.example. dig.out.test$n || ret=1
1692if [ $ret -ne 0 ]; then echo_i "failed"; fi
1693status=$((status+ret))
1694
1695nextpart ns2/named.run >/dev/null
1696
1697n=$((n+1))
1698echo_i "Changing label of domain dom15.example. from 'dom15label1' to 'dom15label2' ($n)"
1699ret=0
1700$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1701    server 10.53.0.1 ${PORT}
1702    update delete dom15label1.zones.catalog1.example. 3600 IN PTR dom15.example.
1703    update add dom15label2.zones.catalog1.example. 3600 IN PTR dom15.example.
1704    send
1705END
1706if [ $ret -ne 0 ]; then echo_i "failed"; fi
1707status=$((status+ret))
1708
1709n=$((n+1))
1710echo_i "waiting for secondary to sync up ($n)"
1711ret=0
1712wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1713if [ $ret -ne 0 ]; then echo_i "failed"; fi
1714status=$((status+ret))
1715
1716n=$((n+1))
1717echo_i "checking that dom15.example. is served by secondary ($n)"
1718ret=0
1719wait_for_soa @10.53.0.2 dom15.example. dig.out.test$n || ret=1
1720if [ $ret -ne 0 ]; then echo_i "failed"; fi
1721status=$((status+ret))
1722
1723##########################################################################
1724echo_i "Testing recreation of a manually deleted zone after a reload"
1725n=$((n+1))
1726echo_i "checking that dom16.example. is not served by primary ($n)"
1727ret=0
1728wait_for_no_soa @10.53.0.1 dom16.example. dig.out.test$n || ret=1
1729if [ $ret -ne 0 ]; then echo_i "failed"; fi
1730status=$((status+ret))
1731
1732n=$((n+1))
1733echo_i "Adding a domain dom16.example. to primary ns1 via RNDC ($n)"
1734ret=0
1735echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom16.example.db
1736echo "@ IN NS invalid." >> ns1/dom16.example.db
1737echo "@ IN A 192.0.2.1" >> ns1/dom16.example.db
1738rndccmd 10.53.0.1 addzone dom16.example. '{type primary; file "dom16.example.db";};' || ret=1
1739if [ $ret -ne 0 ]; then echo_i "failed"; fi
1740status=$((status+ret))
1741
1742n=$((n+1))
1743echo_i "checking that dom16.example. is now served by primary ns1 ($n)"
1744ret=0
1745wait_for_soa @10.53.0.1 dom16.example. dig.out.test$n || ret=1
1746if [ $ret -ne 0 ]; then echo_i "failed"; fi
1747status=$((status+ret))
1748
1749nextpart ns2/named.run >/dev/null
1750
1751n=$((n+1))
1752echo_i "Adding domain dom16.example. to catalog1 zone with ns1 as primary ($n)"
1753ret=0
1754$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1755    server 10.53.0.1 ${PORT}
1756    update add efe725d0cf430ffb113b9bcf59266f066a21216b.zones.catalog1.example. 3600 IN PTR dom16.example.
1757    update add masters.efe725d0cf430ffb113b9bcf59266f066a21216b.zones.catalog1.example. 3600 IN A 10.53.0.1
1758    send
1759END
1760if [ $ret -ne 0 ]; then echo_i "failed"; fi
1761status=$((status+ret))
1762
1763n=$((n+1))
1764echo_i "waiting for secondary to sync up ($n)"
1765ret=0
1766wait_for_message ns2/named.run  "catz: adding zone 'dom16.example' from catalog 'catalog1.example'" &&
1767wait_for_message ns2/named.run  "transfer of 'dom16.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1768if [ $ret -ne 0 ]; then echo_i "failed"; fi
1769status=$((status+ret))
1770
1771nextpart ns2/named.run >/dev/null
1772
1773n=$((n+1))
1774echo_i "checking that dom16.example. is served by secondary and that it's the one from ns1 ($n)"
1775ret=0
1776wait_for_a @10.53.0.2 dom16.example. dig.out.test$n || ret=1
1777grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1778if [ $ret -ne 0 ]; then echo_i "failed"; fi
1779status=$((status+ret))
1780
1781nextpart ns2/named.run >/dev/null
1782
1783echo_i "Deleting dom16.example. from secondary ns2 via RNDC ($n)"
1784ret=0
1785rndccmd 10.53.0.2 delzone dom16.example. >/dev/null 2>&1 || ret=1
1786if [ $ret -ne 0 ]; then echo_i "failed"; fi
1787status=$((status+ret))
1788
1789n=$((n+1))
1790echo_i "checking that dom16.example. is no longer served by secondary ($n)"
1791ret=0
1792wait_for_no_soa @10.53.0.2 dom16.example. dig.out.test$n || ret=1
1793if [ $ret -ne 0 ]; then echo_i "failed"; fi
1794status=$((status+ret))
1795
1796nextpart ns2/named.run >/dev/null
1797
1798echo_i "Reloading secondary ns2 via RNDC ($n)"
1799ret=0
1800rndccmd 10.53.0.2 reload >/dev/null 2>&1 || ret=1
1801if [ $ret -ne 0 ]; then echo_i "failed"; fi
1802status=$((status+ret))
1803
1804n=$((n+1))
1805echo_i "waiting for secondary to sync up ($n)"
1806ret=0
1807wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1808if [ $ret -ne 0 ]; then echo_i "failed"; fi
1809status=$((status+ret))
1810
1811n=$((n+1))
1812echo_i "checking that dom16.example. is served by secondary and that it's the one from ns1 ($n)"
1813ret=0
1814wait_for_a @10.53.0.2 dom16.example. dig.out.test$n || ret=1
1815grep "192.0.2.1" dig.out.test$n > /dev/null || ret=1
1816if [ $ret -ne 0 ]; then echo_i "failed"; fi
1817status=$((status+ret))
1818
1819nextpart ns2/named.run >/dev/null
1820
1821n=$((n+1))
1822echo_i "Deleting domain dom16.example. from catalog1 ($n)"
1823ret=0
1824$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1825    server 10.53.0.1 ${PORT}
1826    update delete efe725d0cf430ffb113b9bcf59266f066a21216b.zones.catalog1.example. 3600 IN PTR dom16.example.
1827    update delete masters.efe725d0cf430ffb113b9bcf59266f066a21216b.zones.catalog1.example. 3600 IN A 10.53.0.1
1828    send
1829END
1830if [ $ret -ne 0 ]; then echo_i "failed"; fi
1831status=$((status+ret))
1832
1833n=$((n+1))
1834echo_i "waiting for secondary to sync up ($n)"
1835ret=0
1836wait_for_message ns2/named.run  "catz: update_from_db: new zone merged" || ret=1
1837if [ $ret -ne 0 ]; then echo_i "failed"; fi
1838status=$((status+ret))
1839
1840n=$((n+1))
1841echo_i "checking that dom16.example. is no longer served by secondary ($n)"
1842ret=0
1843wait_for_no_soa @10.53.0.2 dom16.example. dig.out.test$n || ret=1
1844if [ $ret -ne 0 ]; then echo_i "failed"; fi
1845status=$((status+ret))
1846
1847n=$((n+1))
1848echo_i "checking that reconfig can delete and restore catalog zone configuration ($n)"
1849ret=0
1850copy_setports ns2/named2.conf.in ns2/named.conf
1851rndccmd 10.53.0.2 reconfig || ret=1
1852copy_setports ns2/named1.conf.in ns2/named.conf
1853rndccmd 10.53.0.2 reconfig || ret=1
1854if [ $ret -ne 0 ]; then echo_i "failed"; fi
1855status=$((status+ret))
1856
1857#########################################################################
1858
1859nextpart ns2/named.run >/dev/null
1860
1861n=$((n+1))
1862echo_i "Adding a dom19.example. to primary via RNDC ($n)"
1863ret=0
1864# enough initial content for IXFR response when TXT record is added below
1865echo "@ 3600 IN SOA . . 1 3600 3600 3600 3600" > ns1/dom19.example.db
1866echo "@ 3600 IN NS invalid." >> ns1/dom19.example.db
1867echo "foo 3600 IN TXT some content here" >> ns1/dom19.example.db
1868echo "bar 3600 IN TXT some content here" >> ns1/dom19.example.db
1869echo "xxx 3600 IN TXT some content here" >> ns1/dom19.example.db
1870echo "yyy 3600 IN TXT some content here" >> ns1/dom19.example.db
1871rndccmd 10.53.0.1 addzone dom19.example. '{ type primary; file "dom19.example.db"; allow-transfer { key tsig_key; }; allow-update { any; }; notify explicit; also-notify { 10.53.0.2; }; };' || ret=1
1872if [ $ret -ne 0 ]; then echo_i "failed"; fi
1873status=$((status+ret))
1874
1875n=$((n+1))
1876echo_i "add an entry to the restored catalog zone ($n)"
1877ret=0
1878$NSUPDATE -d <<END >> nsupdate.out.test$n 2>&1 || ret=1
1879    server 10.53.0.1 ${PORT}
1880    update add 09da0a318e5333a9a7f6c14c385d69f6933e8b72.zones.catalog1.example. 3600 IN PTR dom19.example.
1881    update add label1.masters.09da0a318e5333a9a7f6c14c385d69f6933e8b72.zones.catalog1.example. 3600 IN A 10.53.0.1
1882    update add label1.masters.09da0a318e5333a9a7f6c14c385d69f6933e8b72.zones.catalog1.example. 3600 IN TXT "tsig_key"
1883    send
1884END
1885if [ $ret -ne 0 ]; then echo_i "failed"; fi
1886status=$((status+ret))
1887
1888n=$((n+1))
1889echo_i "waiting for secondary to sync up ($n)"
1890ret=0
1891wait_for_message ns2/named.run "catz: adding zone 'dom19.example' from catalog 'catalog1.example'" &&
1892wait_for_message ns2/named.run "transfer of 'dom19.example/IN' from 10.53.0.1#${PORT}: Transfer status: success" || ret=1
1893if [ $ret -ne 0 ]; then echo_i "failed"; fi
1894status=$((status+ret))
1895
1896##########################################################################
1897# GL #3777
1898nextpart ns4/named.run >/dev/null
1899
1900n=$((n+1))
1901echo_i "Adding domain self.example. to catalog-self zone without updating the serial ($n)"
1902ret=0
1903echo "self.zones.catalog-self.example. 3600 IN PTR self.example." >> ns4/catalog-self.example.db
1904rndccmd 10.53.0.4 reload || ret=1
1905
1906n=$((n+1))
1907echo_i "Issuing another rndc reload command after 1 second ($n)"
1908sleep 1
1909rndccmd 10.53.0.4 reload || ret=1
1910if [ $ret -ne 0 ]; then echo_i "failed"; fi
1911status=$((status+ret))
1912
1913##########################################################################
1914echo_i "exit status: $status"
1915[ $status -eq 0 ] || exit 1
1916