/usr/share/perl5/App/AllKnowingDNS/Util.pm is in all-knowing-dns 1.7-1.
This file is owned by root:root, with mode 0o644.
The actual contents of the file can be viewed below.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 | # vim:ts=4:sw=4:expandtab
package App::AllKnowingDNS::Util;
use strict;
use warnings;
use Exporter 'import';
use App::AllKnowingDNS::Config;
use App::AllKnowingDNS::Zone;
use NetAddr::IP::Util qw(ipv6_aton);
use v5.10;
=head1 NAME
App::AllKnowingDNS::Util - utility functions
=head1 DESCRIPTION
Note: User documentation is in L<all-knowing-dns>(1).
=head1 FUNCTIONS
=cut
our @EXPORT = qw(parse_config netmask_to_ptrzone);
=head2 parse_config($lines)
Parses a block of text as configfile.
Returns a corresponding App::AllKnowingDNS::Config object.
=cut
sub parse_config {
my ($input) = @_;
my $config = App::AllKnowingDNS::Config->new;
my @lines = split("\n", $input);
my $current_zone;
for my $line (@lines) {
# Strip whitespace.
$line =~ s/^\s+//;
# Ignore comments.
next if substr($line, 0, 1) eq '#';
# Skip empty lines
next if length($line) == 0;
# If we are not currently parsing a zone, only the 'network' keyword is
# appropriate.
if (!defined($current_zone) &&
!($line =~ /^network/i) && !($line =~ /^listen/i)) {
say STDERR qq|all-knowing-dns: CONFIG: Expected 'network' or 'listen' keyword in line "$line"|;
next;
}
if (my ($address) = ($line =~ /^listen (.*)/i)) {
$config->add_listen_address(lc $address);
next;
}
if (my ($network) = ($line =~ /^network (.*)/i)) {
# The current zone is done now, if any.
$config->add_zone($current_zone) if defined($current_zone);
$current_zone = App::AllKnowingDNS::Zone->new(
network => lc $network,
);
next;
}
if (my ($resolves_to) = ($line =~ /^resolves to (.*)/i)) {
# We explicitly don’t lowercase the DNS names to which PTR entries
# will resolve, since some universities seem to have a fetish for
# uppercase DNS names… :)
$current_zone->resolves_to($resolves_to);
next;
}
if (my ($upstream_dns) = ($line =~ /^with upstream (.*)/i)) {
$current_zone->upstream_dns(lc $upstream_dns);
next;
}
}
$config->add_zone($current_zone) if defined($current_zone);
return $config;
}
=head2 netmask_to_ptrzone($netmask)
Converts the given netmask to a PTR zone.
Example:
my $ptrzone = netmask_to_ptrzone('2001:4d88:100e:ccc0::/64');
say $ptrzone; # 0.c.c.c.e.0.0.1.8.8.d.4.1.0.0.2.ip6.arpa
=cut
sub netmask_to_ptrzone {
my ($netmask) = @_;
my ($address, $mask) = ($netmask =~ m,^([^/]+)/([0-9]+),);
if (($mask % 16) != 0) {
say STDERR "all-knowing-dns: ERROR: Only netmasks which " .
"are dividable by 16 are supported!";
exit 1;
}
my @components = unpack("n8", ipv6_aton($address));
# A nibble is a 4-bit aggregation, that is, one "hex digit".
my @nibbles = map { ((($_ & 0xF000) >> 12),
(($_ & 0x0F00) >> 8),
(($_ & 0x00F0) >> 4),
(($_ & 0x000F) >> 0)) } @components;
# Only keep ($mask / 4) digits. E.g., for a /64 network, keep 16 nibbles.
splice(@nibbles, ($mask / 4));
return join('.', map { sprintf('%x', $_) } reverse @nibbles) . '.ip6.arpa';
}
1
|