Commit 9268297b authored by Mark Andrews's avatar Mark Andrews

4379. [bug] An INSIST could be triggered if a zone contains

                        RRSIG records with expiry fields that loop
                        using serial number arithmetic. [RT #40571]
parent 531074d1
4379. [bug] An INSIST could be triggered if a zone contains
RRSIG records with expiry fields that loop
using serial number arithmetic. [RT #40571]
4378. [contrib] #include <isc/string.h> for strlcat in zone2ldap.c.
[RT #42525]
......
......@@ -141,5 +141,34 @@ n=`expr $n + 1`
if [ $ret != 0 ]; then echo "I:failed"; fi
status=`expr $status + $ret`
echo "I:checking that expirations that loop using serial arithmetic are handled ($n)"
ret=0
q=-q
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
test $ret -eq 1 || $CHECKZONE $q dyn.example.net zones/crashzone.db || ret=1
n=`expr $n + 1`
if [ $ret != 0 ]; then echo "I:failed"; fi
status=`expr $status + $ret`
echo "I:exit status: $status"
exit $status
dyn.example.net. 7200 IN SOA ns1.example.net. hostmaster.example.net. (
6 ; serial
43200 ; refresh (12 hours)
1800 ; retry (30 minutes)
1209600 ; expire (2 weeks)
7200 ; minimum (2 hours)
)
7200 RRSIG SOA 7 3 7200 2010 20100225214229 30323 dyn.example.net.
7200 NS ns1.example.net.
7200 NS ns2.example.net.
3600 RRSIG DNSKEY 7 3 3600 20100227180048 (
20100221180048 52935 dyn.example.net.
MuyIUCa3XlttWuSnaQegQnRgTrTsx0Mj4EGI
fwtZs2H3L079Y/brqMvtlIGxtlr9meLg43oo
jX1w48ilerzf1PwYhtVpFefZTgmClK0h2ej4
Ho9Qh4/6snesVj06kWsQDkhuVs58zHmhRtEy
P4YlqP/R1CAk166RhwSmGuSx1O8= )
0 NSEC3PARAM 1 0 10 76931F
ns1.dyn.example.net. 7200 IN A 1.0.0.5
7200 AAAA 2001:db8::53
7200 RRSIG AAAA 7 4 7200 20100227180048 (
20100221180048 30323 dyn.example.net.
dk1DfG0y9qjCi3VD4e9B1NGKWEig7q8hFdaR
3hElCIzGlflvgHRiE7iTJxDMB+kTA0by4BMZ
yssUuXP2FMlB2g== )
ns2.dyn.example.net. 7200 IN A 1.2.0.6
y.dyn.example.net. 7200 IN A 1.2.3.5
z.dyn.example.net. 7200 IN A 1.2.3.6
A54T6DKFVU4QCKFFNJ0KEU0FH0I4OJSN.dyn.example.net. 7200 IN NSEC3 1 0 10 76931F AJHVGTICN6K0VDA53GCHFMT219SRRQLM A RRSIG
7200 RRSIG NSEC3 7 4 7200 00100227180048 (
20100221180048 30323 dyn.example.net.
9BhZcQdLwRPU/Dz38uMis/nCcddyhKEm0Zb+
Mhh3V3OsGI202cebTaxbwVEbQQOeowpUmf8l
AmK/cNX7+IS2rw== )
AJHVGTICN6K0VDA53GCHFMT219SRRQLM.dyn.example.net. 7200 IN NSEC3 1 0 10 76931F FQ7RBG86KRMACA1NAAKP2KQRQALBA0C7 A RRSIG
FQ7RBG86KRMACA1NAAKP2KQRQALBA0C7.dyn.example.net. 7200 RRSIG NSEC3 7 4 7200 20100227180048 (
20100221180048 30323 dyn.example.net.
577WZnTQemStx+diON9rEGXAGnU7C0KLjrFL
VyhocnBnNtxJS8eRMSWvb9XuYCMNhYKOurtt
Ar4qh4VW1+unmA== )
I7A7A184GGMI35K1E3IR650LKO7NOB5R.dyn.example.net. 7200 IN NSEC3 1 0 10 76931F IMQ912BREQP1POLAH3RMONG;UED541AS A RRSIG
IMQ912BREQP1POLAH3RMONG3UED541AS.dyn.example.net. 7200 IN NSEC3 1 0 10 76931F S3USV4M1HLVJ8F88EDSG8N9PVQRQ20N7 A RRSIG
7200 RRSIG NSEC3 7 4 7200 20100227180048 (
20100221180048 30323 dyn.example.net.
smsg35snQ9PpeG2r8ZGxBl44pwSReh/1rIil
u/n8aa5nKbBpkqtbcc7q1OpUgb1Q7+Tl/wes
kB6bJA== )
S3USV4M1HLVJ8F88EDSG8N9PVQRQ20N7.dyn.example.net. 7200 RRSIG NSEC3 7 4 7200 20100227180048 (
20100221180048 30323 dyn.example.net.
XalRIESpdeVK1aNbwu9ym2SpK981Y127rKua
xsoals0Zn2tTjF9wpOYVGVOto3FcWBbyKD1g
69BTRlv634UIOw== )
T320G5LC07QE1BLR074KORIJTG9DPTI9.dyn.example.net. 7200 IN NSEC3 1 0 10 76931F A54T6DKFVU4QCAFFNJ0KEU0FH0I4OJSN NS SOA RRSIG DNSKEY NSEC3PARAM
......@@ -70,6 +70,7 @@
#include <dns/rdatastruct.h>
#include <dns/result.h>
#include <dns/stats.h>
#include <dns/time.h>
#include <dns/version.h>
#include <dns/view.h>
#include <dns/zone.h>
......@@ -416,6 +417,7 @@ typedef struct rdatasetheader {
unsigned int is_mmapped : 1;
unsigned int next_is_relative : 1;
unsigned int node_is_relative : 1;
unsigned int resign_lsb : 1;
/*%<
* We don't use the LIST macros, because the LIST structure has
* both head and tail pointers, and is doubly linked.
......@@ -1086,7 +1088,8 @@ resign_sooner(void *v1, void *v2) {
rdatasetheader_t *h1 = v1;
rdatasetheader_t *h2 = v2;
if (isc_serial_lt(h1->resign, h2->resign))
if (h1->resign < h2->resign ||
(h1->resign == h2->resign && h1->resign_lsb < h2->resign_lsb))
return (ISC_TRUE);
return (ISC_FALSE);
}
......@@ -3251,7 +3254,7 @@ bind_rdataset(dns_rbtdb_t *rbtdb, dns_rbtnode_t *node,
*/
if (RESIGN(header)) {
rdataset->attributes |= DNS_RDATASETATTR_RESIGN;
rdataset->resign = header->resign;
rdataset->resign = (header->resign << 1) | header->resign_lsb;
} else
rdataset->resign = 0;
}
......@@ -5613,7 +5616,8 @@ printnode(dns_db_t *db, dns_dbnode_t *node, FILE *out) {
current->rdh_ttl,
current->trust,
current->attributes,
current->resign);
(current->resign << 1) |
current->resign_lsb);
current = current->down;
} while (current != NULL);
}
......@@ -6236,8 +6240,11 @@ add32(dns_rbtdb_t *rbtdb, dns_rbtnode_t *rbtnode, rbtdb_version_t *rbtversion,
update_newheader(newheader, header);
if (loading && RESIGN(newheader) &&
RESIGN(header) &&
header->resign < newheader->resign)
header->resign < newheader->resign) {
newheader->resign = header->resign;
newheader->resign_lsb =
header->resign_lsb;
}
} else {
free_rdataset(rbtdb, rbtdb->common.mctx,
newheader);
......@@ -6651,12 +6658,17 @@ addrdataset(dns_db_t *db, dns_dbnode_t *node, dns_dbversion_t *version,
if ((rdataset->attributes & DNS_RDATASETATTR_RESIGN) != 0) {
newheader->attributes |= RDATASET_ATTR_RESIGN;
newheader->resign = rdataset->resign;
} else
newheader->resign =
dns_time64_from32(rdataset->resign) >> 1;
newheader->resign_lsb = rdataset->resign & 0x1;
} else {
newheader->resign = 0;
newheader->resign_lsb = 0;
}
} else {
newheader->serial = 1;
newheader->resign = 0;
newheader->resign_lsb = 0;
if ((rdataset->attributes & DNS_RDATASETATTR_PREFETCH) != 0)
newheader->attributes |= RDATASET_ATTR_PREFETCH;
if ((rdataset->attributes & DNS_RDATASETATTR_NEGATIVE) != 0)
......@@ -6830,9 +6842,12 @@ subtractrdataset(dns_db_t *db, dns_dbnode_t *node, dns_dbversion_t *version,
newheader->node = rbtnode;
if ((rdataset->attributes & DNS_RDATASETATTR_RESIGN) != 0) {
newheader->attributes |= RDATASET_ATTR_RESIGN;
newheader->resign = rdataset->resign;
} else
newheader->resign = dns_time64_from32(rdataset->resign) >> 1;
newheader->resign_lsb = rdataset->resign & 0x1;
} else {
newheader->resign = 0;
newheader->resign_lsb = 0;
}
NODE_LOCK(&rbtdb->node_locks[rbtnode->locknum].lock,
isc_rwlocktype_write);
......@@ -6921,6 +6936,7 @@ subtractrdataset(dns_db_t *db, dns_dbnode_t *node, dns_dbversion_t *version,
newheader->additional_glue = NULL;
newheader->node = rbtnode;
newheader->resign = 0;
newheader->resign_lsb = 0;
newheader->last_used = 0;
} else {
free_rdataset(rbtdb, rbtdb->common.mctx, newheader);
......@@ -7241,9 +7257,12 @@ loading_addrdataset(void *arg, dns_name_t *name, dns_rdataset_t *rdataset) {
if ((rdataset->attributes & DNS_RDATASETATTR_RESIGN) != 0) {
newheader->attributes |= RDATASET_ATTR_RESIGN;
newheader->resign = rdataset->resign;
} else
newheader->resign = dns_time64_from32(rdataset->resign) >> 1;
newheader->resign_lsb = rdataset->resign & 0x1;
} else {
newheader->resign = 0;
newheader->resign_lsb = 0;
}
result = add32(rbtdb, node, rbtdb->current_version, newheader,
DNS_DBADD_MERGE, ISC_TRUE, NULL, 0);
......@@ -7906,7 +7925,8 @@ setsigningtime(dns_db_t *db, dns_rdataset_t *rdataset, isc_stdtime_t resign) {
isc_rwlocktype_write);
oldresign = header->resign;
header->resign = resign;
header->resign = dns_time64_from32(resign) >> 1;
header->resign_lsb = resign & 0x1;
if (header->heap_index != 0) {
INSIST(RESIGN(header));
if (resign == 0) {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment