xref: /minix3/external/bsd/bind/dist/contrib/scripts/check5011.pl (revision 00b67f09dd46474d133c95011a48590a8e8f94c7)
1*00b67f09SDavid van Moolenbroek#!/usr/bin/perl
2*00b67f09SDavid van Moolenbroek
3*00b67f09SDavid van Moolenbroekuse warnings;
4*00b67f09SDavid van Moolenbroekuse strict;
5*00b67f09SDavid van Moolenbroek
6*00b67f09SDavid van Moolenbroekuse POSIX qw(strftime);
7*00b67f09SDavid van Moolenbroekmy $now = strftime "%Y%m%d%H%M%S", gmtime;
8*00b67f09SDavid van Moolenbroek
9*00b67f09SDavid van Moolenbroeksub ext8601 ($) {
10*00b67f09SDavid van Moolenbroek	my $d = shift;
11*00b67f09SDavid van Moolenbroek	$d =~ s{(....)(..)(..)(..)(..)(..)}
12*00b67f09SDavid van Moolenbroek	       {$1-$2-$3.$4:$5:$6+0000};
13*00b67f09SDavid van Moolenbroek	return $d;
14*00b67f09SDavid van Moolenbroek}
15*00b67f09SDavid van Moolenbroek
16*00b67f09SDavid van Moolenbroeksub getkey ($$) {
17*00b67f09SDavid van Moolenbroek	my $h = shift;
18*00b67f09SDavid van Moolenbroek	my $k = shift;
19*00b67f09SDavid van Moolenbroek	m{\s+(\d+)\s+(\d+)\s+(\d+)\s+[(]\s*$};
20*00b67f09SDavid van Moolenbroek	$k->{flags}     = $1;
21*00b67f09SDavid van Moolenbroek	$k->{protocol}  = $2;
22*00b67f09SDavid van Moolenbroek	$k->{algorithm} = $3;
23*00b67f09SDavid van Moolenbroek	my $data = "(";
24*00b67f09SDavid van Moolenbroek	while (<$h>) {
25*00b67f09SDavid van Moolenbroek		s{^\s+}{};
26*00b67f09SDavid van Moolenbroek		s{\s+$}{};
27*00b67f09SDavid van Moolenbroek		last if m{^[)]};
28*00b67f09SDavid van Moolenbroek		$data .= $_;
29*00b67f09SDavid van Moolenbroek	}
30*00b67f09SDavid van Moolenbroek	m{ alg = (\S+); key id = (\d+)};
31*00b67f09SDavid van Moolenbroek	$k->{alg}  = $1;
32*00b67f09SDavid van Moolenbroek	$k->{id}   = $2;
33*00b67f09SDavid van Moolenbroek	$k->{data} = $data;
34*00b67f09SDavid van Moolenbroek	return $k;
35*00b67f09SDavid van Moolenbroek}
36*00b67f09SDavid van Moolenbroek
37*00b67f09SDavid van Moolenbroeksub fmtkey ($) {
38*00b67f09SDavid van Moolenbroek	my $k = shift;
39*00b67f09SDavid van Moolenbroek	return sprintf "%16s tag %s", $k->{name}, $k->{id};
40*00b67f09SDavid van Moolenbroek}
41*00b67f09SDavid van Moolenbroek
42*00b67f09SDavid van Moolenbroeksub printstatus ($) {
43*00b67f09SDavid van Moolenbroek	my $a = shift;
44*00b67f09SDavid van Moolenbroek	if ($a->{removehd} ne "19700101000000") {
45*00b67f09SDavid van Moolenbroek		printf " untrusted and to be removed at %s\n", ext8601 $a->{removehd};
46*00b67f09SDavid van Moolenbroek	} elsif ($a->{addhd} lt $now) {
47*00b67f09SDavid van Moolenbroek		printf " trusted\n";
48*00b67f09SDavid van Moolenbroek	} else {
49*00b67f09SDavid van Moolenbroek		printf " waiting for %s\n", ext8601 $a->{addhd};
50*00b67f09SDavid van Moolenbroek	}
51*00b67f09SDavid van Moolenbroek}
52*00b67f09SDavid van Moolenbroek
53*00b67f09SDavid van Moolenbroeksub digkeys ($) {
54*00b67f09SDavid van Moolenbroek	my $name = shift;
55*00b67f09SDavid van Moolenbroek	my $keys;
56*00b67f09SDavid van Moolenbroek	open my $d, "-|", qw{dig +multiline DNSKEY}, $name;
57*00b67f09SDavid van Moolenbroek	while (<$d>) {
58*00b67f09SDavid van Moolenbroek		next unless m{^([a-z0-9.-]*)\s+\d+\s+IN\s+DNSKEY\s+};
59*00b67f09SDavid van Moolenbroek		next unless $name eq $1;
60*00b67f09SDavid van Moolenbroek		push @$keys, getkey $d, { name => $name };
61*00b67f09SDavid van Moolenbroek	}
62*00b67f09SDavid van Moolenbroek	return $keys;
63*00b67f09SDavid van Moolenbroek}
64*00b67f09SDavid van Moolenbroek
65*00b67f09SDavid van Moolenbroekmy $anchor;
66*00b67f09SDavid van Moolenbroekmy $owner = ".";
67*00b67f09SDavid van Moolenbroekwhile (<>) {
68*00b67f09SDavid van Moolenbroek	next unless m{^([a-z0-9.-]*)\s+KEYDATA\s+(\d+)\s+(\d+)\s+(\d+)\s+};
69*00b67f09SDavid van Moolenbroek	my $k = getkey *ARGV, {
70*00b67f09SDavid van Moolenbroek		name     => $1,
71*00b67f09SDavid van Moolenbroek		refresh  => $2,
72*00b67f09SDavid van Moolenbroek		addhd    => $3,
73*00b67f09SDavid van Moolenbroek		removehd => $4,
74*00b67f09SDavid van Moolenbroek	};
75*00b67f09SDavid van Moolenbroek	if ($k->{name} eq "") {
76*00b67f09SDavid van Moolenbroek		$k->{name} = $owner;
77*00b67f09SDavid van Moolenbroek	} else {
78*00b67f09SDavid van Moolenbroek		$owner = $k->{name};
79*00b67f09SDavid van Moolenbroek	}
80*00b67f09SDavid van Moolenbroek	$k->{name} =~ s{[.]*$}{.};
81*00b67f09SDavid van Moolenbroek	push @{$anchor->{$k->{name}}}, $k;
82*00b67f09SDavid van Moolenbroek}
83*00b67f09SDavid van Moolenbroek
84*00b67f09SDavid van Moolenbroekfor my $name (keys %$anchor) {
85*00b67f09SDavid van Moolenbroek	my $keys = digkeys $name;
86*00b67f09SDavid van Moolenbroek	my $anchors = $anchor->{$name};
87*00b67f09SDavid van Moolenbroek	for my $k (@$keys) {
88*00b67f09SDavid van Moolenbroek		if ($k->{flags} & 1) {
89*00b67f09SDavid van Moolenbroek			printf "%s %s", fmtkey $k, $k->{alg};
90*00b67f09SDavid van Moolenbroek		} else {
91*00b67f09SDavid van Moolenbroek			# ZSK - skipping
92*00b67f09SDavid van Moolenbroek			next;
93*00b67f09SDavid van Moolenbroek		}
94*00b67f09SDavid van Moolenbroek		if ($k->{flags} & 512) {
95*00b67f09SDavid van Moolenbroek			print " revoked;";
96*00b67f09SDavid van Moolenbroek		}
97*00b67f09SDavid van Moolenbroek		my $a;
98*00b67f09SDavid van Moolenbroek		for my $t (@$anchors) {
99*00b67f09SDavid van Moolenbroek			if ($t->{data} eq $k->{data} and
100*00b67f09SDavid van Moolenbroek			    $t->{protocol} eq $k->{protocol} and
101*00b67f09SDavid van Moolenbroek			    $t->{algorithm} eq $k->{algorithm}) {
102*00b67f09SDavid van Moolenbroek				$t->{matched} = 1;
103*00b67f09SDavid van Moolenbroek				$a = $t;
104*00b67f09SDavid van Moolenbroek				last;
105*00b67f09SDavid van Moolenbroek			}
106*00b67f09SDavid van Moolenbroek		}
107*00b67f09SDavid van Moolenbroek		if (not defined $a) {
108*00b67f09SDavid van Moolenbroek			print " no trust anchor\n";
109*00b67f09SDavid van Moolenbroek			next;
110*00b67f09SDavid van Moolenbroek		}
111*00b67f09SDavid van Moolenbroek		printstatus $a;
112*00b67f09SDavid van Moolenbroek	}
113*00b67f09SDavid van Moolenbroek	for my $a (@$anchors) {
114*00b67f09SDavid van Moolenbroek		next if $a->{matched};
115*00b67f09SDavid van Moolenbroek		printf "%s %s missing;", fmtkey $a, $a->{alg};
116*00b67f09SDavid van Moolenbroek		printstatus $a;
117*00b67f09SDavid van Moolenbroek	}
118*00b67f09SDavid van Moolenbroek}
119*00b67f09SDavid van Moolenbroek
120*00b67f09SDavid van Moolenbroekexit;
121*00b67f09SDavid van Moolenbroek
122*00b67f09SDavid van Moolenbroek__END__
123*00b67f09SDavid van Moolenbroek
124*00b67f09SDavid van Moolenbroek=head1 NAME
125*00b67f09SDavid van Moolenbroek
126*00b67f09SDavid van Moolenbroekcheck5011 - summarize DNSSEC trust anchor status
127*00b67f09SDavid van Moolenbroek
128*00b67f09SDavid van Moolenbroek=head1 SYNOPSIS
129*00b67f09SDavid van Moolenbroek
130*00b67f09SDavid van Moolenbroekcheck5011 <I<managed-keys.bind>>
131*00b67f09SDavid van Moolenbroek
132*00b67f09SDavid van Moolenbroek=head1 DESCRIPTION
133*00b67f09SDavid van Moolenbroek
134*00b67f09SDavid van MoolenbroekThe BIND managed-keys file contains DNSSEC trust anchors
135*00b67f09SDavid van Moolenbroekthat can be automatically updated according to RFC 5011. The
136*00b67f09SDavid van MoolenbroekB<check5011> program reads this file and prints a summary of the
137*00b67f09SDavid van Moolenbroekstatus of the trust anchors. It fetches the corresponding
138*00b67f09SDavid van MoolenbroekDNSKEY records using B<dig> and compares them to the trust anchors.
139*00b67f09SDavid van Moolenbroek
140*00b67f09SDavid van MoolenbroekEach key is printed on a line with its name, its tag, and its
141*00b67f09SDavid van Moolenbroekalgorithm, followed by a summary of its status.
142*00b67f09SDavid van Moolenbroek
143*00b67f09SDavid van Moolenbroek=over
144*00b67f09SDavid van Moolenbroek
145*00b67f09SDavid van Moolenbroek=item C<trusted>
146*00b67f09SDavid van Moolenbroek
147*00b67f09SDavid van MoolenbroekThe key is currently trusted.
148*00b67f09SDavid van Moolenbroek
149*00b67f09SDavid van Moolenbroek=item C<waiting for ...>
150*00b67f09SDavid van Moolenbroek
151*00b67f09SDavid van MoolenbroekThe key is new, and B<named> is waiting for the "add hold-down" period
152*00b67f09SDavid van Moolenbroekto pass before the key will be trusted.
153*00b67f09SDavid van Moolenbroek
154*00b67f09SDavid van Moolenbroek=item C<untrusted and to be removed at ...>
155*00b67f09SDavid van Moolenbroek
156*00b67f09SDavid van MoolenbroekThe key was revoked and will be removed at the stated time.
157*00b67f09SDavid van Moolenbroek
158*00b67f09SDavid van Moolenbroek=item C<no trust anchor>
159*00b67f09SDavid van Moolenbroek
160*00b67f09SDavid van MoolenbroekThe key is present in the DNS but not in the managed-keys file.
161*00b67f09SDavid van Moolenbroek
162*00b67f09SDavid van Moolenbroek=item C<revoked>
163*00b67f09SDavid van Moolenbroek
164*00b67f09SDavid van MoolenbroekThe key has its revoked flag set. This is printed before the key's
165*00b67f09SDavid van Moolenbroektrust anchor status which should normally be C<untrusted...> if
166*00b67f09SDavid van MoolenbroekB<named> has observed the revocation.
167*00b67f09SDavid van Moolenbroek
168*00b67f09SDavid van Moolenbroek=item C<missing>
169*00b67f09SDavid van Moolenbroek
170*00b67f09SDavid van MoolenbroekThere is no DNSKEY record for this trust anchor. This is printed
171*00b67f09SDavid van Moolenbroekbefore the key's trust anchor status.
172*00b67f09SDavid van Moolenbroek
173*00b67f09SDavid van Moolenbroek=back
174*00b67f09SDavid van Moolenbroek
175*00b67f09SDavid van MoolenbroekBy default the managed keys are stored in a file called
176*00b67f09SDavid van MoolenbroekF<managed-keys.bind> in B<named>'s working directory. This location
177*00b67f09SDavid van Moolenbroekcan be changed with B<named>'s B<managed-keys-directory> option. If
178*00b67f09SDavid van Moolenbroekyou are using views the file may be named with the SHA256 hash of a
179*00b67f09SDavid van Moolenbroekview name with a F<.mkeys> extension added.
180*00b67f09SDavid van Moolenbroek
181*00b67f09SDavid van Moolenbroek=head1 AUTHOR
182*00b67f09SDavid van Moolenbroek
183*00b67f09SDavid van Moolenbroek=over
184*00b67f09SDavid van Moolenbroek
185*00b67f09SDavid van Moolenbroek=item Written by Tony Finch <fanf2@cam.ac.uk> <dot@dotat.at>
186*00b67f09SDavid van Moolenbroek
187*00b67f09SDavid van Moolenbroek=item at the University of Cambridge Computing Service.
188*00b67f09SDavid van Moolenbroek
189*00b67f09SDavid van Moolenbroek=item You may do anything with this. It has no warranty.
190*00b67f09SDavid van Moolenbroek
191*00b67f09SDavid van Moolenbroek=item L<http://creativecommons.org/publicdomain/zero/1.0/>
192*00b67f09SDavid van Moolenbroek
193*00b67f09SDavid van Moolenbroek=back
194*00b67f09SDavid van Moolenbroek
195*00b67f09SDavid van Moolenbroek=head1 SEE ALSO
196*00b67f09SDavid van Moolenbroek
197*00b67f09SDavid van Moolenbroekdig(1), named(8)
198*00b67f09SDavid van Moolenbroek
199*00b67f09SDavid van Moolenbroek=cut
200