- Timestamp:
- 11/24/20 17:29:20 (4 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/bind-import
r812 r813 31 31 32 32 my $zname = shift @ARGV; 33 die "usage: bind-import zonename\n" if !$zname; 33 34 my $rev = 'n'; 34 35 my $zid; … … 66 67 my $curlabel = ''; 67 68 69 my $i = 0; 70 68 71 while (<>) { 69 72 chomp; 70 73 next if /^\s*$/; 71 next if /^\s*;/; 74 next if /^\s*;/; # comments 75 next if /^\s*\(/; # SOA closing. arguably should do some more targeted voodoo when parsing the SOA details 76 72 77 if (my ($macro,$mdetail) = (/^\s*\$(TTL|ORIGIN|INCLUDE|GENERATE)\s+(.+)/) ) { 73 78 # macro sort of thing; $TTL and $ORIGIN most common. $INCLUDE is a thing, expect it to be rare in live use tho … … 96 101 next; 97 102 } 103 my $origrec = $_; 98 104 # skip stale records that have no value 99 105 next if /^ip-192-168-1(12|20)-\d+/; … … 101 107 # records must begin in the first column, no leading whitespace 102 108 my ($name) = /^([\w\@_.-]+)\s/; 109 110 print "$i ($_)\n\t$name"; 111 # foo IN A 1.2.3.4 112 # IN A 2.3.4.5 113 # = 114 # foo.zone. IN A 1.2.3.4 115 # foo.zone. IN A 2.3.4.5 116 117 118 # magic name! 119 $name = $zname if $name eq '@'; 120 103 121 # append zone name to record name if missing AND not dot-terminated; 104 122 # this happens automagically for forward zones, but not reverse because Reasons. (fixme?) 105 123 # suck up and deal with the error if the dot-termiated name is out of zone; should be 106 124 # impossible with valid BIND zone file but... 107 $name .= ".$zname" if $name !~ /$zname$/ && $zname !~ /\.$/; 108 $name = $zname if /^\s*IN/; 109 $name = $zname if /^\@/; 125 if ($name !~ /\.$/) { 126 $name .= ".$zname" if $name !~ /$zname$/; 127 } else { 128 warn "skipping out-of-zone record:\n\t($_)\n" if $name !~ /$zname\.$/; 129 next; 130 } 131 132 # fatal error. if there is no previous label, we can by definition not set 133 # the current label based on it. this can only happen on the very first 134 # record, following records will *ALWAYS* have a previous label 135 if (/^\s+[A-Z]/) { 136 die "bad first record ($_): no previous label\n" if !$prevlabel; 137 $name = $prevlabel; 138 } 139 140 last if $i > 2; 141 110 142 s/^([\w\@_.-]+)\s+//; 143 144 $prevlabel = $curlabel; 111 145 # by convention the optional TTL leads the optional class, but they're apparently swappable. 112 146 my ($ttl) = /^(\d+)?\s/; … … 124 158 } 125 159 if ($class ne 'IN') { 126 print "Non-Internet class records not supported, you weirdo\n";160 warn "Non-Internet class ($class) records not supported:\n\t$origrec\n"; 127 161 next; 128 162 } … … 133 167 my ($type) = /([A-Z-]+)\s/; 134 168 if (!$reverse_typemap{$type}) { 135 print "Unknown type $type, skipping\n($_)\n";169 warn "Unknown type $type, skipping\n\t($_)\n"; 136 170 next; 137 171 } … … 162 196 163 197 if ($type eq 'SOA') { 164 165 } 198 my ($ns, $adminmail) = ($rdata =~ /([\w.]+)\s+([\w.]+)\s+\(/); 199 die "Can't parse gibberish SOAish record: $_\n" if !$ns; 200 $rdata =~ s/([\w.]+)\s+([\w.]+)\s+\(\s*//; 201 202 # There are probably more efficient ways to do this but the SOA record 203 # format is essentially character based, not line-based. 204 # In theory the SOA serial etc may be spread over up to 5 lines, in any combination. 205 206 # Parse fields from $rdata if present 207 my @soabits; 208 my @soafirst = split /\s+/, $rdata; 209 while (my $f = shift @soafirst) { 210 last if $f !~ /^\d/; 211 push @soabits, $f; 212 } 213 214 # Read more lines if we don't have enough SOA fields filled 215 while (scalar(@soabits) < 5) { 216 my $tmp = <>; 217 $tmp =~ s/^\s*//; 218 my @tmpsoa = split /\s+/, $tmp; 219 while (my $f = shift @tmpsoa) { 220 last if $f !~ /^\d/; 221 push @soabits, $f; 222 } 223 if (scalar(@soabits) == 5) { 224 last; 225 } 226 } 227 } # SOA 166 228 167 229 # Quotes may arguably be syntactically required, but they're not actually part of the record data 168 if ($itype == 16) {230 elsif ($type eq 'TXT') { 169 231 $rdata =~ s/^"//; 170 232 $rdata =~ s/"$//; … … 172 234 173 235 # temp hack for hosts file 174 if ($type eq 'A') {236 elsif ($type eq 'A') { 175 237 # if ($amap{$name}) { 176 238 # print "urp: dupe name $name $rdata\n"; … … 180 242 push @{$namemap{$rdata}}, $name; 181 243 } 182 if ($type eq 'CNAME') {244 elsif ($type eq 'CNAME') { 183 245 push @{$cmap{$rdata}}, $name; 184 246 } … … 198 260 print "$code: $msg\n"; 199 261 } 262 $i++; 200 263 } 201 264
Note:
See TracChangeset
for help on using the changeset viewer.