Changeset 815


Ignore:
Timestamp:
11/25/20 10:54:26 (3 years ago)
Author:
Kris Deugau
Message:

/trunk

Eigth sampled iteration of bind-import

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/bind-import

    r814 r815  
    3939my %cmap;
    4040
     41##fixme:  this is wrong, BIND zone files are generally complete and we're adding.  merging records is an entire fridge full of worms.
    4142if ($zname =~ /\.arpa\.?$/ || $zname =~ m,^[\d./]+$,) {
    4243  $rev = 'y';
     
    6061my $zonettl = 900;
    6162my $defttl = $zonettl;
    62 my $recbase = $zname;   # to append to unqualified names
     63my $origin = $zname;    # to append to unqualified names
    6364
    6465# need to spin up a full state machine-ish thing, because BIND zone files are all about context
     
    7374  next if /^\s*$/;
    7475  next if /^\s*;/;      # comments
    75   next if /^\s*\(/;     # SOA closing.  arguably should do some more targeted voodoo when parsing the SOA details
    76 
     76  next if /^\s*\)/;     # SOA closing.  arguably should do some more targeted voodoo when parsing the SOA details
     77
     78print "($_)\n";
    7779  if (my ($macro,$mdetail) = (/^\s*\$(TTL|ORIGIN|INCLUDE|GENERATE)\s+(.+)/) ) {
    7880    # macro sort of thing;  $TTL and $ORIGIN most common.  $INCLUDE is a thing, expect it to be rare in live use tho
    7981    if ($macro eq 'TTL') {
     82      $mdetail =~ s/\s*;.+$//;
    8083      if ($mdetail =~ /^\d+$/) {
    8184        $defttl = $mdetail;
     
    8790# between . and the root domain we were told we're importing;  anyone using such
    8891# a mess outside the root servers is clearly insane
    89 # handled cases:
    90 #   $ORIGIN .
    91 #   $ORIGIN [zonedomain].
    92 #   $ORIGIN [subdomain.zonedomain].
    93       if ($mdetail eq '.' || $mdetail =~ /$zname\.$/ || $zname =~ /$mdetail\.$/) {
    94         $recbase = $mdetail;
     92
     93# $ORIGIN supports cascading/nesting, by watching for fully-qualified names vs partial names.
     94
     95print "origin ($mdetail)\n";
     96      if ($mdetail =~ /\.$/) {
     97        $origin = $mdetail;
    9598      } else {
    96         # if we continue, we either use an $ORIGIN that's out of zone, or ignore it and potentially publish incorrect records.
    97         die "bad \$ORIGIN: $_\n";
    98       }
     99        # append current origin to unqualified origin
     100        $origin = "$mdetail.$origin";
     101      }
     102
     103#      if ($mdetail eq '.' || $mdetail =~ /$zname\.$/ || $zname =~ /$mdetail\.$/) {
     104#        $origin = $mdetail;
     105#      } else {
     106#        # if we continue, we either use an $ORIGIN that's out of zone, or ignore it and potentially publish incorrect records.
     107#        die "bad \$ORIGIN: $_\n";
     108#      }
     109
    99110    }
    100111    # not handling $INCLUDE or $GENERATE (altho the latter seems to be mostly a less-flexible version of the template types)
    101112    next;
    102113  }
     114
    103115  my $origrec = $_;
     116
    104117  # skip stale records that have no value
    105118  next if /^ip-192-168-1(12|20)-\d+/;
    106119  next if /ip.add.re.\d+\s*$/;
    107   # records must begin in the first column, no leading whitespace
    108   my ($name) = /^([\w\@_.-]+)\s/;
     120
     121  # leading whitespace indicates "same label as last record"
     122  if (/^\s/) {
     123    $curlabel = $prevlabel;
     124  } else {
     125    ($curlabel) = /^([\w\@_.-]+)\s/;
     126  }
     127
     128  # magic name!
     129  $curlabel = "$zname." if $curlabel eq '@';
     130
     131  # append $ORIGIN if name is not fully qualified.
     132  if ($curlabel !~ /\.$/) {
     133    $curlabel .= $origin;
     134  }
     135
     136  # check for zone scope.  skip bad records.
     137  if ($curlabel !~ /$zname.$/) {
     138    warn "bad record $origrec, maybe bad \$ORIGIN?\n";
     139    next;
     140  }
     141
     142#  # records must begin in the first column, no leading whitespace
     143#  my ($name) = /^([\w\@_.-]+)\s/;
    109144
    110145# foo IN A 1.2.3.4
     
    114149# foo.zone. IN A 2.3.4.5
    115150
    116   # "empty" label records inherit the previous label
    117   # RRs start in the first column by definition, so leading whitespace indicates an inherited label
    118   if (/^\s+/) {
    119     # fatal error.  if there is no previous label, we can by definition not set
    120     # the current label based on it.  this can only happen on the very first
    121     # record, following records will *ALWAYS* have a previous label
    122     die "bad first record ($_):  no previous label\n" if !$prevlabel;
    123     $name = $prevlabel;
    124   }
    125 
    126 print "$i ($_)\n\t$name";
    127 
    128   # magic name!
    129   $name = $zname if $name eq '@';
    130 
    131 
    132 
    133   # append zone name to record name if missing AND not dot-terminated;
    134   # this happens automagically for forward zones, but not reverse because Reasons.  (fixme?)
    135   # suck up and deal with the error if the dot-termiated name is out of zone;  should be
    136   # impossible with valid BIND zone file but...
    137   if ($name !~ /\.$/) {
    138     $name .= ".$zname" if $name !~ /$zname$/;
    139   } else {
    140     warn "skipping out-of-zone record:\n\t($_)\n" if $name !~ /$zname\.$/;
    141     next;
    142   }
    143 
    144 
    145 last if $i > 5;
     151#  # "empty" label records inherit the previous label
     152#  # RRs start in the first column by definition, so leading whitespace indicates an inherited label
     153#  if (/^\s+/) {
     154#    # fatal error.  if there is no previous label, we can by definition not set
     155#    # the current label based on it.  this can only happen on the very first
     156#    # record, following records will *ALWAYS* have a previous label
     157#    die "bad first record ($_):  no previous label\n" if !$prevlabel;
     158#    $name = $prevlabel;
     159#  }
     160
     161print "$i ($_)\n\t$curlabel";
     162
     163
     164
     165
     166#  # append zone name to record name if missing AND not dot-terminated;
     167#  # this happens automagically for forward zones, but not reverse because Reasons.  (fixme?)
     168#  # suck up and deal with the error if the dot-termiated name is out of zone;  should be
     169#  # impossible with valid BIND zone file but...
     170#  if ($name !~ /\.$/) {
     171#    $name .= ".$zname" if $name !~ /$zname$/;
     172#  } else {
     173#    warn "skipping out-of-zone record:\n\t($_)\n" if $name !~ /$zname\.$/;
     174#    next;
     175#  }
     176
     177last if ++$i > 5;
     178
    146179
    147180  s/^([\w\@_.-]+)\s+//;
    148181
     182my $nc = 0;
     183my %seenatoms;
     184my $badrec;
     185my $curatom = 'class';
     186##fixme:  maybe wrap this in an eval() instead of the warn/badrec/last bits?
     187for (my ($atom) = /^([\w\d]+)\s/; $nc < 3; $nc++) {
     188  if ($atom =~ /^\d+$/) {
     189    if (defined($seenatoms{ttl})) {
     190      warn "bad record ($origrec)\n";
     191      $badrec = 1;
     192      last;
     193    } else {
     194      if ($curatom ne 'class' && $curatom ne 'ttl') {
     195        warn "bad record ($origrec)\n";
     196        $badrec = 1;
     197        last;
     198      }
     199      $curatom = 'ttl';
     200      $seenatoms{ttl} = $atom;
     201    }
     202  }
     203  if ($atom =~ /^IN|CS|CH|HS$/) {
     204    if ($atom =~ /CS|CH|HS/) {
     205      warn "unsupported class $atom in record ($origrec)\n";
     206      $badrec = 1;
     207      last;
     208    }
     209    $curatom = 'class';
     210  }
     211  if ($reverse_typemap{$atom}) {
     212    print "dbg: type $atom\n";
     213  }
     214#  my $itype = $reverse_typemap{$type};
     215}
     216
     217next if $badrec;
     218
     219
    149220##fixme:  drop curlabel?  not sure it's needed
    150 $curlabel = $name;
     221#$curlabel = $name;
    151222$prevlabel = $curlabel;
    152223##todo:  BIND conflates a repeated label with repeating the TTL too.  Matter of opinion whether that's really correct or not.
     224
    153225
    154226
     
    248320#    print "urp:  dupe name $name $rdata\n";
    249321#  } else {
    250     push @{$amap{$name}}, $rdata;
     322    push @{$amap{$curlabel}}, $rdata;
    251323#  }
    252   push @{$namemap{$rdata}}, $name;
     324  push @{$namemap{$rdata}}, $curlabel;
    253325}
    254326elsif ($type eq 'CNAME') {
    255   push @{$cmap{$rdata}}, $name;
     327  push @{$cmap{$rdata}}, $curlabel;
    256328}
    257329
     
    264336    my ($code, $msg);
    265337    if ($rev eq 'n') {
    266       ($code,$msg) = $dnsdb->addRec('n', $rev, $zid, \$name, \$itype, \$rdata, $ttl);
     338      ($code,$msg) = $dnsdb->addRec('n', $rev, $zid, \$curlabel, \$itype, \$rdata, $ttl);
    267339    } else {
    268       ($code,$msg) = $dnsdb->addRec('n', $rev, $zid, \$rdata, \$itype, \$name, $ttl);
     340      ($code,$msg) = $dnsdb->addRec('n', $rev, $zid, \$rdata, \$itype, \$curlabel, $ttl);
    269341    }
    270342    print "$code: $msg\n";
Note: See TracChangeset for help on using the changeset viewer.