From: Nicki Křížek Date: Wed, 11 Jun 2025 14:33:53 +0000 (+0200) Subject: Isolate rollover-multisigner test case X-Git-Tag: v9.21.11~38^2~1 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=86c3c1da77019a5803d356d26a31023f92c62e91;p=thirdparty%2Fbind9.git Isolate rollover-multisigner test case --- diff --git a/bin/tests/system/rollover-multisigner/common.py b/bin/tests/system/rollover-multisigner/common.py new file mode 120000 index 00000000000..64b8084c5ac --- /dev/null +++ b/bin/tests/system/rollover-multisigner/common.py @@ -0,0 +1 @@ +../rollover/common.py \ No newline at end of file diff --git a/bin/tests/system/rollover-multisigner/ns3/kasp.conf.j2 b/bin/tests/system/rollover-multisigner/ns3/kasp.conf.j2 new file mode 100644 index 00000000000..22c8f5e4b06 --- /dev/null +++ b/bin/tests/system/rollover-multisigner/ns3/kasp.conf.j2 @@ -0,0 +1,22 @@ +/* + * Copyright (C) Internet Systems Consortium, Inc. ("ISC") + * + * SPDX-License-Identifier: MPL-2.0 + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, you can obtain one at https://mozilla.org/MPL/2.0/. + * + * See the COPYRIGHT file distributed with this work for additional + * information regarding copyright ownership. + */ + +dnssec-policy "multisigner-model2" { + dnskey-ttl 3600; + inline-signing no; + + keys { + ksk key-directory lifetime unlimited algorithm @DEFAULT_ALGORITHM@ tag-range 32768 65535; + zsk key-directory lifetime unlimited algorithm @DEFAULT_ALGORITHM@ tag-range 32768 65535; + }; +}; diff --git a/bin/tests/system/rollover-multisigner/ns3/named.common.conf.j2 b/bin/tests/system/rollover-multisigner/ns3/named.common.conf.j2 new file mode 120000 index 00000000000..5dc26178cb1 --- /dev/null +++ b/bin/tests/system/rollover-multisigner/ns3/named.common.conf.j2 @@ -0,0 +1 @@ +../../rollover/ns3/named.common.conf.j2 \ No newline at end of file diff --git a/bin/tests/system/rollover-multisigner/ns3/named.conf.j2 b/bin/tests/system/rollover-multisigner/ns3/named.conf.j2 new file mode 100644 index 00000000000..bbc08501aff --- /dev/null +++ b/bin/tests/system/rollover-multisigner/ns3/named.conf.j2 @@ -0,0 +1,34 @@ +/* + * Copyright (C) Internet Systems Consortium, Inc. ("ISC") + * + * SPDX-License-Identifier: MPL-2.0 + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, you can obtain one at https://mozilla.org/MPL/2.0/. + * + * See the COPYRIGHT file distributed with this work for additional + * information regarding copyright ownership. + */ + +include "kasp.conf"; +include "named.common.conf"; + +/* RFC 8901 Multi-signer Model 2. */ +zone "multisigner-model2.kasp" { + type primary; + file "multisigner-model2.kasp.db"; + dnssec-policy "multisigner-model2"; + allow-update { any; }; +}; + +/* + * A zone that starts with keys that have tags that are + * outside of the desired multi-signer key tag range. + */ +zone "single-to-multisigner.kasp" { + type primary; + file "single-to-multisigner.kasp.db"; + dnssec-policy "multisigner-model2"; + allow-update { any; }; +}; diff --git a/bin/tests/system/rollover-multisigner/ns3/template.db.in b/bin/tests/system/rollover-multisigner/ns3/template.db.in new file mode 120000 index 00000000000..ce6d526285a --- /dev/null +++ b/bin/tests/system/rollover-multisigner/ns3/template.db.in @@ -0,0 +1 @@ +../../rollover/ns3/template.db.in \ No newline at end of file diff --git a/bin/tests/system/rollover-multisigner/setup.sh b/bin/tests/system/rollover-multisigner/setup.sh new file mode 100644 index 00000000000..d9937adb088 --- /dev/null +++ b/bin/tests/system/rollover-multisigner/setup.sh @@ -0,0 +1,67 @@ +#!/bin/sh -e + +# Copyright (C) Internet Systems Consortium, Inc. ("ISC") +# +# SPDX-License-Identifier: MPL-2.0 +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, you can obtain one at https://mozilla.org/MPL/2.0/. +# +# See the COPYRIGHT file distributed with this work for additional +# information regarding copyright ownership. + +# shellcheck source=conf.sh +. ../conf.sh + +cd "ns3" + +setup() { + zone="$1" + echo_i "setting up zone: $zone" + zonefile="${zone}.db" + infile="${zone}.db.infile" + echo "$zone" >>zones +} + +# Set in the key state files the Predecessor/Successor fields. +# Key $1 is the predecessor of key $2. +key_successor() { + id1=$(keyfile_to_key_id "$1") + id2=$(keyfile_to_key_id "$2") + echo "Predecessor: ${id1}" >>"${2}.state" + echo "Successor: ${id2}" >>"${1}.state" +} + +# Make lines shorter by storing key states in environment variables. +H="HIDDEN" +R="RUMOURED" +O="OMNIPRESENT" +U="UNRETENTIVE" + +# Multi-signer zones. +setup "multisigner-model2.kasp" +cp template.db.in "$zonefile" +KSK=$($KEYGEN -a $DEFAULT_ALGORITHM -f KSK -L 3600 -M 32768:65535 $zone 2>keygen.out.$zone.1) +ZSK=$($KEYGEN -a $DEFAULT_ALGORITHM -L 3600 -M 32768:65535 $zone 2>keygen.out.$zone.2) +cat "${KSK}.key" | grep -v ";.*" >>"${zone}.db" +cat "${ZSK}.key" | grep -v ";.*" >>"${zone}.db" +# Import a ZSK of another provider into the DNSKEY RRset. +ZSK1=$($KEYGEN -K ../ -a $DEFAULT_ALGORITHM -L 3600 -M 0:32767 $zone 2>keygen.out.$zone.3) +cat "../${ZSK1}.key" | grep -v ";.*" >>"${zone}.db" + +# We are changing an existing single-signed zone to multi-signed +# zone where the key tags do not match the dnssec-policy key tag range +setup single-to-multisigner.kasp +T="now-7d" +S="now-8635mi" # T - 1d5m +keytimes="-P $T -A $T" +cdstimes="-P sync $S" +KSK=$($KEYGEN -a $DEFAULT_ALGORITHM -M 0:32767 -L 3600 -f KSK $keytimes $cdstimes $zone 2>keygen.out.$zone.1) +ZSK=$($KEYGEN -a $DEFAULT_ALGORITHM -M 0:32767 -L 3600 $keytimes $zone 2>keygen.out.$zone.2) +$SETTIME -s -g $O -d $O $T -k $O $T -r $O $T "$KSK" >settime.out.$zone.1 2>&1 +$SETTIME -s -g $O -k $O $T -z $O $T "$ZSK" >settime.out.$zone.2 2>&1 +cat template.db.in "${KSK}.key" "${ZSK}.key" >"$infile" +$SIGNER -PS -z -x -s now-2w -e now-1mi -o $zone -f "${zonefile}" $infile >signer.out.$zone.1 2>&1 +echo "Lifetime: 0" >>"${KSK}".state +echo "Lifetime: 0" >>"${ZSK}".state diff --git a/bin/tests/system/rollover-multisigner/tests_rollover_multisigner.py b/bin/tests/system/rollover-multisigner/tests_rollover_multisigner.py new file mode 100644 index 00000000000..9c2403ca689 --- /dev/null +++ b/bin/tests/system/rollover-multisigner/tests_rollover_multisigner.py @@ -0,0 +1,173 @@ +# Copyright (C) Internet Systems Consortium, Inc. ("ISC") +# +# SPDX-License-Identifier: MPL-2.0 +# +# This Source Code Form is subject to the terms of the Mozilla Public +# License, v. 2.0. If a copy of the MPL was not distributed with this +# file, you can obtain one at https://mozilla.org/MPL/2.0/. +# +# See the COPYRIGHT file distributed with this work for additional +# information regarding copyright ownership. + +# pylint: disable=redefined-outer-name,unused-import + +from datetime import timedelta +import os + +import pytest + +pytest.importorskip("dns", minversion="2.0.0") +import dns.update + +import isctest +from isctest.kasp import Iret +from common import ( + pytestmark, + alg, + size, +) + + +def test_rollover_multisigner(servers, alg, size): + server = servers["ns3"] + policy = "multisigner-model2" + config = { + "dnskey-ttl": timedelta(hours=1), + "ds-ttl": timedelta(days=1), + "max-zone-ttl": timedelta(days=1), + "parent-propagation-delay": timedelta(hours=1), + "publish-safety": timedelta(hours=1), + "retire-safety": timedelta(hours=1), + "signatures-refresh": timedelta(days=5), + "signatures-validity": timedelta(days=14), + "zone-propagation-delay": timedelta(minutes=5), + } + ttl = int(config["dnskey-ttl"].total_seconds()) + + offset = -timedelta(days=7) + offval = int(offset.total_seconds()) + + def keygen(zone): + keygen_command = [ + os.environ.get("KEYGEN"), + "-a", + alg, + "-L", + "3600", + "-M", + "0:32767", + zone, + ] + + return isctest.run.cmd(keygen_command).stdout.decode("utf-8") + + zone = "multisigner-model2.kasp" + + isctest.kasp.check_dnssec_verify(server, zone) + + key_properties = [ + f"ksk unlimited {alg} {size} goal:omnipresent dnskey:rumoured krrsig:rumoured ds:hidden tag-range:32768-65535", + f"zsk unlimited {alg} {size} goal:omnipresent dnskey:rumoured zrrsig:rumoured tag-range:32768-65535", + ] + expected = isctest.kasp.policy_to_properties(ttl, key_properties) + + newprops = [f"zsk unlimited {alg} {size} tag-range:0-32767"] + expected2 = isctest.kasp.policy_to_properties(ttl, newprops) + expected2[0].properties["private"] = False + expected2[0].properties["legacy"] = True + expected = expected + expected2 + + ownkeys = isctest.kasp.keydir_to_keylist(zone, server.identifier) + extkeys = isctest.kasp.keydir_to_keylist(zone) + keys = ownkeys + extkeys + ksks = [k for k in ownkeys if k.is_ksk()] + zsks = [k for k in ownkeys if not k.is_ksk()] + zsks = zsks + extkeys + + isctest.kasp.check_keys(zone, keys, expected) + for kp in expected: + kp.set_expected_keytimes(config) + isctest.kasp.check_keytimes(keys, expected) + isctest.kasp.check_dnssecstatus(server, zone, keys, policy=policy) + isctest.kasp.check_apex(server, zone, ksks, zsks) + isctest.kasp.check_subdomain(server, zone, ksks, zsks) + + # Update zone with ZSK from another provider for zone. + out = keygen(zone) + newkeys = isctest.kasp.keystr_to_keylist(out) + newprops = [f"zsk unlimited {alg} {size} tag-range:0-32767"] + expected2 = isctest.kasp.policy_to_properties(ttl, newprops) + expected2[0].properties["private"] = False + expected2[0].properties["legacy"] = True + expected = expected + expected2 + + dnskey = newkeys[0].dnskey().split() + rdata = " ".join(dnskey[4:]) + + update_msg = dns.update.UpdateMessage(zone) + update_msg.add(f"{dnskey[0]}", 3600, "DNSKEY", rdata) + server.nsupdate(update_msg) + + isctest.kasp.check_dnssec_verify(server, zone) + + keys = keys + newkeys + zsks = zsks + newkeys + isctest.kasp.check_keys(zone, keys, expected) + isctest.kasp.check_apex(server, zone, ksks, zsks) + isctest.kasp.check_subdomain(server, zone, ksks, zsks) + + # Remove ZSKs from the other providers for zone. + dnskey2 = extkeys[0].dnskey().split() + rdata2 = " ".join(dnskey2[4:]) + update_msg = dns.update.UpdateMessage(zone) + update_msg.delete(f"{dnskey[0]}", "DNSKEY", rdata) + update_msg.delete(f"{dnskey2[0]}", "DNSKEY", rdata2) + server.nsupdate(update_msg) + + isctest.kasp.check_dnssec_verify(server, zone) + + expected = isctest.kasp.policy_to_properties(ttl, key_properties) + keys = ownkeys + ksks = [k for k in ownkeys if k.is_ksk()] + zsks = [k for k in ownkeys if not k.is_ksk()] + isctest.kasp.check_keys(zone, keys, expected) + isctest.kasp.check_apex(server, zone, ksks, zsks) + isctest.kasp.check_subdomain(server, zone, ksks, zsks) + + # A zone transitioning from single-signed to multi-signed. We should have + # the old omnipresent keys outside of the desired key range and the new + # keys in the desired key range. + zone = "single-to-multisigner.kasp" + + isctest.kasp.check_dnssec_verify(server, zone) + + key_properties = [ + f"ksk unlimited {alg} {size} goal:omnipresent dnskey:rumoured krrsig:rumoured ds:hidden tag-range:32768-65535", + f"zsk unlimited {alg} {size} goal:omnipresent dnskey:rumoured zrrsig:hidden tag-range:32768-65535", + f"ksk unlimited {alg} {size} goal:hidden dnskey:omnipresent krrsig:omnipresent ds:omnipresent tag-range:0-32767 offset:{offval}", + f"zsk unlimited {alg} {size} goal:hidden dnskey:omnipresent zrrsig:omnipresent tag-range:0-32767 offset:{offval}", + ] + expected = isctest.kasp.policy_to_properties(ttl, key_properties) + keys = isctest.kasp.keydir_to_keylist(zone, server.identifier) + ksks = [k for k in keys if k.is_ksk()] + zsks = [k for k in keys if not k.is_ksk()] + + isctest.kasp.check_keys(zone, keys, expected) + + for kp in expected: + kp.set_expected_keytimes(config) + + start = expected[0].key.get_timing("Created") + expected[2].timing["Retired"] = start + expected[2].timing["Removed"] = expected[2].timing["Retired"] + Iret( + config, zsk=False, ksk=True + ) + expected[3].timing["Retired"] = start + expected[3].timing["Removed"] = expected[3].timing["Retired"] + Iret( + config, zsk=True, ksk=False + ) + + isctest.kasp.check_keytimes(keys, expected) + isctest.kasp.check_dnssecstatus(server, zone, keys, policy=policy) + isctest.kasp.check_apex(server, zone, ksks, zsks) + isctest.kasp.check_subdomain(server, zone, ksks, zsks) diff --git a/bin/tests/system/rollover/ns3/kasp.conf.j2 b/bin/tests/system/rollover/ns3/kasp.conf.j2 index 2ab26877f0e..bbecf098a8f 100644 --- a/bin/tests/system/rollover/ns3/kasp.conf.j2 +++ b/bin/tests/system/rollover/ns3/kasp.conf.j2 @@ -19,13 +19,3 @@ dnssec-policy "manual-rollover" { zsk key-directory lifetime unlimited algorithm @DEFAULT_ALGORITHM@; }; }; - -dnssec-policy "multisigner-model2" { - dnskey-ttl 3600; - inline-signing no; - - keys { - ksk key-directory lifetime unlimited algorithm @DEFAULT_ALGORITHM@ tag-range 32768 65535; - zsk key-directory lifetime unlimited algorithm @DEFAULT_ALGORITHM@ tag-range 32768 65535; - }; -}; diff --git a/bin/tests/system/rollover/ns3/named.conf.j2 b/bin/tests/system/rollover/ns3/named.conf.j2 index 63a6909144a..f44a96afd0a 100644 --- a/bin/tests/system/rollover/ns3/named.conf.j2 +++ b/bin/tests/system/rollover/ns3/named.conf.j2 @@ -11,34 +11,11 @@ * information regarding copyright ownership. */ -// NS3 - include "kasp.conf"; - include "named.common.conf"; -/* Manual rollover. */ zone "manual-rollover.kasp" { type primary; file "manual-rollover.kasp.db"; dnssec-policy "manual-rollover"; }; - -/* RFC 8901 Multi-signer Model 2. */ -zone "multisigner-model2.kasp" { - type primary; - file "multisigner-model2.kasp.db"; - dnssec-policy "multisigner-model2"; - allow-update { any; }; -}; - -/* - * A zone that starts with keys that have tags that are - * outside of the desired multi-signer key tag range. - */ -zone "single-to-multisigner.kasp" { - type primary; - file "single-to-multisigner.kasp.db"; - dnssec-policy "multisigner-model2"; - allow-update { any; }; -}; diff --git a/bin/tests/system/rollover/ns3/setup.sh b/bin/tests/system/rollover/ns3/setup.sh index 969b6a7e6c1..59fd259aed4 100644 --- a/bin/tests/system/rollover/ns3/setup.sh +++ b/bin/tests/system/rollover/ns3/setup.sh @@ -52,30 +52,3 @@ private_type_record $zone $DEFAULT_ALGORITHM_NUMBER "$KSK" >>"$infile" private_type_record $zone $DEFAULT_ALGORITHM_NUMBER "$ZSK" >>"$infile" cp $infile $zonefile $SIGNER -PS -x -o $zone -O raw -f "${zonefile}.signed" $infile >signer.out.$zone.1 2>&1 - -# Multi-signer zones. -setup "multisigner-model2.kasp" -cp template.db.in "$zonefile" -KSK=$($KEYGEN -a $DEFAULT_ALGORITHM -f KSK -L 3600 -M 32768:65535 $zone 2>keygen.out.$zone.1) -ZSK=$($KEYGEN -a $DEFAULT_ALGORITHM -L 3600 -M 32768:65535 $zone 2>keygen.out.$zone.2) -cat "${KSK}.key" | grep -v ";.*" >>"${zone}.db" -cat "${ZSK}.key" | grep -v ";.*" >>"${zone}.db" -# Import a ZSK of another provider into the DNSKEY RRset. -ZSK1=$($KEYGEN -K ../ -a $DEFAULT_ALGORITHM -L 3600 -M 0:32767 $zone 2>keygen.out.$zone.3) -cat "../${ZSK1}.key" | grep -v ";.*" >>"${zone}.db" - -# We are changing an existing single-signed zone to multi-signed -# zone where the key tags do not match the dnssec-policy key tag range -setup single-to-multisigner.kasp -T="now-7d" -S="now-8635mi" # T - 1d5m -keytimes="-P $T -A $T" -cdstimes="-P sync $S" -KSK=$($KEYGEN -a $DEFAULT_ALGORITHM -M 0:32767 -L 3600 -f KSK $keytimes $cdstimes $zone 2>keygen.out.$zone.1) -ZSK=$($KEYGEN -a $DEFAULT_ALGORITHM -M 0:32767 -L 3600 $keytimes $zone 2>keygen.out.$zone.2) -$SETTIME -s -g $O -d $O $T -k $O $T -r $O $T "$KSK" >settime.out.$zone.1 2>&1 -$SETTIME -s -g $O -k $O $T -z $O $T "$ZSK" >settime.out.$zone.2 2>&1 -cat template.db.in "${KSK}.key" "${ZSK}.key" >"$infile" -$SIGNER -PS -z -x -s now-2w -e now-1mi -o $zone -f "${zonefile}" $infile >signer.out.$zone.1 2>&1 -echo "Lifetime: 0" >>"${KSK}".state -echo "Lifetime: 0" >>"${ZSK}".state diff --git a/bin/tests/system/rollover/tests_rollover.py b/bin/tests/system/rollover/tests_rollover.py index 025bbb0d7c4..b7804812309 100644 --- a/bin/tests/system/rollover/tests_rollover.py +++ b/bin/tests/system/rollover/tests_rollover.py @@ -9,17 +9,13 @@ # See the COPYRIGHT file distributed with this work for additional # information regarding copyright ownership. -import os - from datetime import timedelta +import os import pytest -pytest.importorskip("dns", minversion="2.0.0") -import dns.update - import isctest -from isctest.kasp import KeyTimingMetadata, Ipub, IpubC, Iret +from isctest.kasp import KeyTimingMetadata, Ipub, Iret from common import pytestmark @@ -161,150 +157,3 @@ def test_rollover_manual(servers): zsk = expected[3].key response = server.rndc(f"dnssec -rollover -key {zsk.tag} {zone}") assert "key is not actively signing" in response - - -def test_rollover_multisigner(servers): - server = servers["ns3"] - policy = "multisigner-model2" - config = { - "dnskey-ttl": timedelta(hours=1), - "ds-ttl": timedelta(days=1), - "max-zone-ttl": timedelta(days=1), - "parent-propagation-delay": timedelta(hours=1), - "publish-safety": timedelta(hours=1), - "retire-safety": timedelta(hours=1), - "signatures-refresh": timedelta(days=5), - "signatures-validity": timedelta(days=14), - "zone-propagation-delay": timedelta(minutes=5), - } - ttl = int(config["dnskey-ttl"].total_seconds()) - alg = os.environ["DEFAULT_ALGORITHM_NUMBER"] - size = os.environ["DEFAULT_BITS"] - - offset = -timedelta(days=7) - offval = int(offset.total_seconds()) - - def keygen(zone): - keygen_command = [ - os.environ.get("KEYGEN"), - "-a", - alg, - "-L", - "3600", - "-M", - "0:32767", - zone, - ] - - return isctest.run.cmd(keygen_command).stdout.decode("utf-8") - - zone = "multisigner-model2.kasp" - - isctest.kasp.check_dnssec_verify(server, zone) - - key_properties = [ - f"ksk unlimited {alg} {size} goal:omnipresent dnskey:rumoured krrsig:rumoured ds:hidden tag-range:32768-65535", - f"zsk unlimited {alg} {size} goal:omnipresent dnskey:rumoured zrrsig:rumoured tag-range:32768-65535", - ] - expected = isctest.kasp.policy_to_properties(ttl, key_properties) - - newprops = [f"zsk unlimited {alg} {size} tag-range:0-32767"] - expected2 = isctest.kasp.policy_to_properties(ttl, newprops) - expected2[0].properties["private"] = False - expected2[0].properties["legacy"] = True - expected = expected + expected2 - - ownkeys = isctest.kasp.keydir_to_keylist(zone, server.identifier) - extkeys = isctest.kasp.keydir_to_keylist(zone) - keys = ownkeys + extkeys - ksks = [k for k in ownkeys if k.is_ksk()] - zsks = [k for k in ownkeys if not k.is_ksk()] - zsks = zsks + extkeys - - isctest.kasp.check_keys(zone, keys, expected) - for kp in expected: - kp.set_expected_keytimes(config) - isctest.kasp.check_keytimes(keys, expected) - isctest.kasp.check_dnssecstatus(server, zone, keys, policy=policy) - isctest.kasp.check_apex(server, zone, ksks, zsks) - isctest.kasp.check_subdomain(server, zone, ksks, zsks) - - # Update zone with ZSK from another provider for zone. - out = keygen(zone) - newkeys = isctest.kasp.keystr_to_keylist(out) - newprops = [f"zsk unlimited {alg} {size} tag-range:0-32767"] - expected2 = isctest.kasp.policy_to_properties(ttl, newprops) - expected2[0].properties["private"] = False - expected2[0].properties["legacy"] = True - expected = expected + expected2 - - dnskey = newkeys[0].dnskey().split() - rdata = " ".join(dnskey[4:]) - - update_msg = dns.update.UpdateMessage(zone) - update_msg.add(f"{dnskey[0]}", 3600, "DNSKEY", rdata) - server.nsupdate(update_msg) - - isctest.kasp.check_dnssec_verify(server, zone) - - keys = keys + newkeys - zsks = zsks + newkeys - isctest.kasp.check_keys(zone, keys, expected) - isctest.kasp.check_apex(server, zone, ksks, zsks) - isctest.kasp.check_subdomain(server, zone, ksks, zsks) - - # Remove ZSKs from the other providers for zone. - dnskey2 = extkeys[0].dnskey().split() - rdata2 = " ".join(dnskey2[4:]) - update_msg = dns.update.UpdateMessage(zone) - update_msg.delete(f"{dnskey[0]}", "DNSKEY", rdata) - update_msg.delete(f"{dnskey2[0]}", "DNSKEY", rdata2) - server.nsupdate(update_msg) - - isctest.kasp.check_dnssec_verify(server, zone) - - expected = isctest.kasp.policy_to_properties(ttl, key_properties) - keys = ownkeys - ksks = [k for k in ownkeys if k.is_ksk()] - zsks = [k for k in ownkeys if not k.is_ksk()] - isctest.kasp.check_keys(zone, keys, expected) - isctest.kasp.check_apex(server, zone, ksks, zsks) - isctest.kasp.check_subdomain(server, zone, ksks, zsks) - - # A zone transitioning from single-signed to multi-signed. We should have - # the old omnipresent keys outside of the desired key range and the new - # keys in the desired key range. - zone = "single-to-multisigner.kasp" - - isctest.kasp.check_dnssec_verify(server, zone) - - key_properties = [ - f"ksk unlimited {alg} {size} goal:omnipresent dnskey:rumoured krrsig:rumoured ds:hidden tag-range:32768-65535", - f"zsk unlimited {alg} {size} goal:omnipresent dnskey:rumoured zrrsig:hidden tag-range:32768-65535", - f"ksk unlimited {alg} {size} goal:hidden dnskey:omnipresent krrsig:omnipresent ds:omnipresent tag-range:0-32767 offset:{offval}", - f"zsk unlimited {alg} {size} goal:hidden dnskey:omnipresent zrrsig:omnipresent tag-range:0-32767 offset:{offval}", - ] - expected = isctest.kasp.policy_to_properties(ttl, key_properties) - keys = isctest.kasp.keydir_to_keylist(zone, server.identifier) - ksks = [k for k in keys if k.is_ksk()] - zsks = [k for k in keys if not k.is_ksk()] - - isctest.kasp.check_keys(zone, keys, expected) - - for kp in expected: - kp.set_expected_keytimes(config) - - start = expected[0].key.get_timing("Created") - expected[2].timing["Retired"] = start - expected[2].timing["Removed"] = expected[2].timing["Retired"] + Iret( - config, zsk=False, ksk=True - ) - expected[3].timing["Retired"] = start - expected[3].timing["Removed"] = expected[3].timing["Retired"] + Iret( - config, zsk=True, ksk=False - ) - - isctest.kasp.check_keytimes(keys, expected) - isctest.kasp.check_dnssecstatus(server, zone, keys, policy=policy) - isctest.kasp.check_apex(server, zone, ksks, zsks) - isctest.kasp.check_subdomain(server, zone, ksks, zsks)