]> git.sesse.net Git - nms/commitdiff
Merge with main branch.
authorEirik Nygaard <eirikn@space>
Tue, 3 Apr 2007 13:37:55 +0000 (15:37 +0200)
committerEirik Nygaard <eirikn@space>
Tue, 3 Apr 2007 13:37:55 +0000 (15:37 +0200)
14 files changed:
.bzrignore [new file with mode: 0644]
config/make-dhcpd.pl
config/make-missing-zones.pl
config/make-named-secondary.pl
config/make-named.pl
config/make-port-config.pl [new file with mode: 0755]
make-all-config.sh [new file with mode: 0755]
mbd/access_list.pl [new file with mode: 0644]
mbd/generate-helper-list.pl [new file with mode: 0755]
mbd/mbd.pl [new file with mode: 0644]
mbd/mbd.pm [new file with mode: 0644]
mbd/nets.pl [new file with mode: 0644]
planning/planning.cpp [changed mode: 0644->0755]
static-switches.txt [new file with mode: 0644]

diff --git a/.bzrignore b/.bzrignore
new file mode 100644 (file)
index 0000000..aff8099
--- /dev/null
@@ -0,0 +1,5 @@
+*-config
+mbd-ports
+patchlist.txt
+switches.txt
+planning/planning
index b31820d1a9fa43cb491a6796eaeb742c4ca28751..3da7111372d9d43ec784ddc34ceeac09b62bd3de 100755 (executable)
@@ -1,63 +1,54 @@
 #! /usr/bin/perl -w
 use strict;
 
-# les inn nettnavn
-my %netnames = ();
-my %netmasks = ();
+my $date = `date --rfc-2822`;
+chomp $date;
+
 my @nets = ();
 open NAMES, "switches.txt"
        or die "switches.txt: $!";
 while (<NAMES>) {
        chomp;
-       /194\.0\.(\d+\.\d+)\s+(\d+)\s+(\S+)/ or next;
-       $netmasks{$1} = $2;
-       $netnames{$1} = $3;
-       push @nets, $1;
+       /87\.76\.(\d+\.\d+)\s+(\d+)\s+(\S+)/ or next;
+       push @nets, {
+               net => $1,
+               netmask => $2,
+               name => $3
+       };
 }      
 
 print <<"EOF";
-# Autogenerated by make-dhcpd.pl. Do not edit manually!
+# Autogenerated by make-dhcpd.pl at $date. Do not edit manually!
 
-option domain-name "tg06.gathering.org";
-option domain-name-servers 194.0.254.2;
+option domain-name "tg07.gathering.org";
+option domain-name-servers 87.76.254.2, 87.76.255.2;
 
-# ddns-update-style none;
-ddns-update-style interim;
+# Netboot FTW
+next-server 87.76.255.18;
+filename "/pxelinux.0";
 
-# extra logging for option 82
-if exists agent.circuit-id
-{
-       log (
-               info,
-               concat (
-                       "option-82 info for ", binary-to-ascii (16, 8, ":", hardware),
-                       ": interface ", binary-to-ascii (10, 8, "/", suffix ( option agent.circuit-id, 2)),
-                       ", VLAN ", binary-to-ascii (10, 16, "", substring( option agent.circuit-id, 2, 2)),
-                       ", switch '", substring( option agent.remote-id, 2, 6),
-                       "', port-name '", substring ( option agent.circuit-id, 2, extract-int ( substring ( option agent.circuit-id, 3, 1 ), 8 ) ),
-                       "'"
-              )
-       );
-}
+ddns-update-style interim;
+omapi-port 7911;
 
 # dnssec-keygen -a HMAC-MD5 -b 128 -n HOST DHCP_UPDATER
 key DHCP_UPDATER {
         algorithm HMAC-MD5.SIG-ALG.REG.INT;
-       secret 5Yz1azvh7mE0IRGffTvtKg==;
+       secret F388UOhaIIKHRH9TDE5PTA==;
 }
 
 default-lease-time 14400;
 max-lease-time 28800;
 
 # Tele-nett
-subnet 194.0.254.0 netmask 255.255.255.0 {
+subnet 87.76.254.0 netmask 255.255.255.0 {
 }
 
 # Server-nett
-subnet 194.0.255.0 netmask 255.255.255.0 {
+subnet 87.76.255.0 netmask 255.255.255.0 {
+       range 87.76.255.240 87.76.255.254;
 }
 
-zone 0.194.in-addr.arpa. {
+zone 76.87.in-addr.arpa. {
        primary 127.0.0.1;
        key DHCP_UPDATER;
 }
@@ -65,97 +56,44 @@ zone 0.194.in-addr.arpa. {
 EOF
 
 for my $net (@nets) {
-       my $domain = $netnames{$net};
+       my $domain = $net->{name};
 
        my ($netmask, $numpc);
-       if ($netmasks{$net} == 24) {
+       if ($net->{netmask} == 24) {
                $netmask = "255.255.255.0";
                $numpc = 256;
-       } elsif ($netmasks{$net} == 25) {
+       } elsif ($net->{netmask} == 25) {
                $netmask = "255.255.255.128";
                $numpc = 128;
-       } elsif ($netmasks{$net} == 26) {
+       } elsif ($net->{netmask} == 26) {
                $netmask = "255.255.255.192";
                $numpc = 64;
        } else {
-               die "Unknown netmask /$netmasks{$net}";
+               die "Unknown netmask /" . $net->{netmask};
        }
 
-       $net =~ /(\d+)\.(\d+)/ or die "Unknown net $net";
+       $net->{net} =~ /(\d+)\.(\d+)/ or die "Unknown net $net";
        my ($majorsubnet,$minorsubnet) = ($1,$2);
-       
-       my $gw = "194.0.$majorsubnet." . ($minorsubnet + 1);
-       my $rangestart = "194.0.$majorsubnet." . ($minorsubnet + 10);
-       my $rangeend = "194.0.$majorsubnet." . ($minorsubnet + $numpc - 2);
-
-       if ($domain =~ /^split:(.*)/) {
-               my @domains = split /,/, $1;
-               for my $d (@domains) {
-                       print <<"EOF";
-zone $d.tg06.gathering.org. {
-       primary 127.0.0.1;
-       key DHCP_UPDATER;
-}
-EOF
-               }
-               print <<"EOF";
-subnet 194.0.$net netmask $netmask {
-       authoritative;
-       option routers $gw;
 
-EOF
-               my $numpc_sub = int($numpc / scalar(@domains));
-               for my $d (@domains) {
-                       print <<"EOF";
-       class "$d" {
-               match if substring ( option agent.circuit-id, 2, extract-int ( substring ( option agent.circuit-id, 3, 1 ), 8 ) ) = "$d";
-       }
-EOF
-               }
-
-               my $i = 0;
-               for my $d (@domains) {
-                       my $rangestart = "194.0.$majorsubnet." . ($minorsubnet + $i * $numpc_sub + 10);
-                       my $rangeend = "194.0.$majorsubnet." . ($minorsubnet + $i * $numpc_sub + $numpc_sub - 2);
-                       
-                       print <<"EOF";
-       pool {
-               allow members of "$d";
-               range $rangestart $rangeend;
-               option domain-name "$d.tg06.gathering.org tg06.gathering.org";
-               ddns-domainname "$d.tg06.gathering.org";
-               ignore client-updates;
-       }
-EOF
-                       ++$i;
-               }
-       } else {
-               print <<"EOF";
-zone $domain.tg06.gathering.org. {
+       # FIXME: Should use Net::CIDR
+       my $gw = "87.76.$majorsubnet." . ($minorsubnet + 1);
+       my $rangestart = "87.76.$majorsubnet." . ($minorsubnet + 10);
+       my $rangeend = "87.76.$majorsubnet." . ($minorsubnet + $numpc - 2);
+
+       print <<"EOF";
+zone $domain.tg07.gathering.org. {
        primary 127.0.0.1;
        key DHCP_UPDATER;
 }
-subnet 194.0.$net netmask $netmask {
+subnet 87.76.$net->{net} netmask $netmask {
        authoritative;
        option routers $gw;
 
        range $rangestart $rangeend;
-       option domain-name "$domain.tg06.gathering.org tg06.gathering.org";
-       ddns-domainname "$domain.tg06.gathering.org";
+       option domain-name "$domain.tg07.gathering.org";
+       ddns-domainname "$domain.tg07.gathering.org";
        ignore client-updates;
+}
 EOF
-
-               # hack for sesse =)
-               if ($net eq '250.0') {
-                       print <<"EOF";
-       host trofast {
-               hardware ethernet 00:0e:0c:36:a7:66;
-               filename "/pxelinux.0";
-               next-server 194.0.255.25;
-       }
-EOF
-               }
-       }
-       
-       print "}\n";
 }
+
index b80939827cab505698484ce6254ab02c73411cac..0ac49318fca71cb2a9afa53bcf7a68e5fa15e129 100755 (executable)
@@ -1,46 +1,43 @@
 #! /usr/bin/perl -w
 use strict;
 
-# les inn nettnavn
-my %netnames = ();
+my $date = `date --rfc-2822`;
+chomp $date;
+
+my @nets = ();
 open NAMES, "switches.txt"
        or die "switches.txt: $!";
 while (<NAMES>) {
        chomp;
-       /194\.0\.(\d+\.\d+)\s+(\S+)\s+(\S+)/ or next;
-       $netnames{$1} = $3;
-}
-close NAMES;
+       /87\.76\.(\d+\.\d+)\s+(\d+)\s+(\S+)/ or next;
+       push @nets, {
+               net => $1,
+               netmask => $2,
+               name => $3
+       };
+}      
 
-for my $net (keys %netnames) {
-       my $domain = $netnames{$net};
-       my @domains;
-       if ($domain =~ /^split:(.*)/) {
-               @domains = split /,/, $1;
-       } else {
-               @domains = ($domain);
-       }
+for my $net (@nets) {
+       my $d = $net->{name};
 
-       for my $d (@domains) {
-               -f "/etc/bind/dynamic/$d.tg06.gathering.org" and next;
+       -f "/etc/bind/dynamic/$d.tg07.gathering.org" and next;
                        
-               print "/etc/bind/dynamic/$d.tg06.gathering.org\n";
-               open ZONE, ">/etc/bind/dynamic/$d.tg06.gathering.org"
-                       or die "/etc/bind/dynamic/$d.tg06.gathering.org";
+       print "/etc/bind/dynamic/$d.tg07.gathering.org\n";
+       open ZONE, ">/etc/bind/dynamic/$d.tg07.gathering.org"
+               or die "/etc/bind/dynamic/$d.tg07.gathering.org";
 
-               print ZONE <<"EOF";
+       print ZONE <<"EOF";
 ; autogenerated and updated from dhcpd -- DO NOT TOUCH!
 \$TTL 3600
-@      IN      SOA     fortran.tg06.gathering.org.     postmaster.fortran.tg06.gathering.org. (
+@      IN      SOA     sysrq.tg07.gathering.org.       abuse.gathering.org. (
                        3   ; serial
                        3600 ; refresh 
                        1800 ; retry
                        608400 ; expire
                        3600 ) ; minimum and default TTL
 
-               IN      NS      fortran.tg06.gathering.org.
-               IN      NS      lisp.tg06.gathering.org.
+               IN      NS      sysrq.tg07.gathering.org.
+               IN      NS      insert.tg07.gathering.org.
 
 EOF
-       }
 }
index 38fda02b1a5d5684ed9352a22c52689adb5b0d06..a9b3c12af32ae7ec91134c084290a97142b4a83d 100755 (executable)
@@ -1,27 +1,29 @@
 #! /usr/bin/perl -w
 use strict;
 
-# les inn nettnavn
-my %netnames = ();
-my %netmasks = ();
+my $date = `date --rfc-2822`;
+chomp $date;
+
 my @nets = ();
 open NAMES, "switches.txt"
-or die "switches.txt: $!";
+       or die "switches.txt: $!";
 while (<NAMES>) {
        chomp;
-       /194\.0\.(\d+\.\d+)\s+(\d+)\s+(\S+)/ or next;
-       $netmasks{$1} = $2;
-       $netnames{$1} = $3;
-       push @nets, $1;
-}
+       /87\.76\.(\d+\.\d+)\s+(\d+)\s+(\S+)/ or next;
+       push @nets, {
+               net => $1,
+               netmask => $2,
+               name => $3
+       };
+}      
 
 print <<"EOF";
-// Autogenerated by make-named-secondary.pl. Do not edit manually! 
+// Autogenerated by make-named-secondary.pl at $date. Do not edit manually! 
 
 options {
         directory "/etc/bind";
        allow-query { any; };
-       allow-transfer { 194.19.3.20; 194.0.255.2; }; 
+       allow-transfer { 194.19.3.20; }; 
        auth-nxdomain no;
        recursion yes;
 
@@ -37,29 +39,54 @@ zone "0.0.127.in-addr.arpa" {
        notify no;
 };
 
-zone "tg06.gathering.org" {
+zone "tg07.gathering.org" {
+       type slave;
+       notify no;
+       masters { 87.76.254.2; };
+       file "tg07.gathering.org";
+};
+
+// linknett
+zone "174.76.87.in-addr.arpa" {
+       type slave;
+       notify no;
+       masters { 87.76.254.2; };
+       file "174.76.87.in-addr.arpa";
+       allow-transfer { 193.0.0.0/22; };
+};
+
+// nett-subnett
+zone "239.76.87.in-addr.arpa" {
        type slave;
        notify no;
-       masters { 194.0.254.2; };
-       file "tg06.gathering.org";
+       masters { 87.76.254.2; };
+       file "239.76.87.in-addr.arpa";
+       allow-transfer { 193.0.0.0/22; };
 };
 
 // serversubnett
-zone "255.0.194.in-addr.arpa" {
+zone "254.76.87.in-addr.arpa" {
        type slave;
        notify no;
-       masters { 194.0.254.2; };
-       file "255.0.194.in-addr.arpa";
-       allow-transfer { 194.0.255.2; 193.0.0.0/22; };
+       masters { 87.76.254.2; };
+       file "254.76.87.in-addr.arpa";
+       allow-transfer { 193.0.0.0/22; };
+};
+zone "255.76.87.in-addr.arpa" {
+       type slave;
+       notify no;
+       masters { 87.76.254.2; };
+       file "255.76.87.in-addr.arpa";
+       allow-transfer { 193.0.0.0/22; };
 };
 
-zone "0.194.in-addr.arpa" {
+zone "76.87.in-addr.arpa" {
        type slave;
        notify no;
-       masters { 194.0.254.2; };
+       masters { 87.76.254.2; };
        allow-update { key DHCP_UPDATER; };
-       file "dynamic/0.194.in-addr.arpa";      
-       allow-transfer { 194.19.3.20; 194.0.255.2; 193.0.0.0/22; };
+       file "dynamic/76.87.in-addr.arpa";      
+       allow-transfer { 194.19.3.20; 193.0.0.0/22; };
 };
 
 key DHCP_UPDATER {
@@ -70,24 +97,16 @@ key DHCP_UPDATER {
 EOF
 
 for my $net (@nets) {
-       my $domain = $netnames{$net};
-       my @domains;
-       if ($domain =~ /^split:(.*)/) {
-               @domains = split /,/, $1;
-       } else {
-               @domains = ($domain);
-       }
-
-       for my $d (@domains) {
-               print <<"EOF";
-zone "$d.tg06.gathering.org" {
+       my $d = $net->{name};
+
+       print <<"EOF";
+zone "$d.tg07.gathering.org" {
        type slave;
        notify no;
-       masters { 194.0.254.2; };
+       masters { 87.76.254.2; };
        allow-update { key DHCP_UPDATER; };
-       file "dynamic/$d.tg06.gathering.org";
-       allow-transfer { 194.19.3.20; 194.0.255.2; };
+       file "dynamic/$d.tg07.gathering.org";
+       allow-transfer { 194.19.3.20; };
 };
 EOF
-       }
 }
index 2099b647769483f55edb4de7993213bb4dc60a12..d2bbf02096abd201508c8770ba8a574f9bfdfb70 100755 (executable)
@@ -1,27 +1,29 @@
 #! /usr/bin/perl -w
 use strict;
 
-# les inn nettnavn
-my %netnames = ();
-my %netmasks = ();
+my $date = `date --rfc-2822`;
+chomp $date;
+
 my @nets = ();
 open NAMES, "switches.txt"
-or die "switches.txt: $!";
+       or die "switches.txt: $!";
 while (<NAMES>) {
        chomp;
-       /194\.0\.(\d+\.\d+)\s+(\d+)\s+(\S+)/ or next;
-       $netmasks{$1} = $2;
-       $netnames{$1} = $3;
-       push @nets, $1;
-}
+       /87\.76\.(\d+\.\d+)\s+(\d+)\s+(\S+)/ or next;
+       push @nets, {
+               net => $1,
+               netmask => $2,
+               name => $3
+       };
+}      
 
 print <<"EOF";
-// Autogenerated by make-named.pl. Do not edit manually! 
+// Autogenerated by make-named.pl at $date. Do not edit manually! 
 
 options {
         directory "/etc/bind";
        allow-query { any; };
-       allow-transfer { 194.19.3.20; 194.0.255.2; }; 
+       allow-transfer { 194.19.3.20; 87.76.255.2; }; 
        auth-nxdomain no;
        recursion yes;
 
@@ -37,54 +39,67 @@ zone "0.0.127.in-addr.arpa" {
        notify no;
 };
 
-zone "tg06.gathering.org" {
+zone "tg07.gathering.org" {
        type master;
-       file "tg06.gathering.org";
+       file "tg07.gathering.org";
        notify yes;
-       allow-transfer { 194.0.255.2; };
+       allow-transfer { 87.76.255.2; };
 };
 
-// serversubnett
-zone "255.0.194.in-addr.arpa" {
+// linknett
+zone "174.76.87.in-addr.arpa" {
        type master;
-       file "255.0.194.in-addr.arpa";
+       file "174.76.87.in-addr.arpa";
        notify yes;
-       allow-transfer { 194.0.255.2; 193.0.0.0/22; };
+       allow-transfer { 87.76.255.2; 193.0.0.0/22; };
 };
 
-zone "0.194.in-addr.arpa" {
+// net-subnett
+zone "239.76.87.in-addr.arpa" {
        type master;
-       allow-update { key DHCP_UPDATER; };
+       file "239.76.87.in-addr.arpa";
+       notify yes;
+       allow-transfer { 87.76.255.2; 193.0.0.0/22; };
+};
+
+// serversubnett
+zone "254.76.87.in-addr.arpa" {
+       type master;
+       file "254.76.87.in-addr.arpa";
        notify yes;
-       file "dynamic/0.194.in-addr.arpa";      
-       allow-transfer { 194.19.3.20; 194.0.255.2; 193.0.0.0/22; };
+       allow-transfer { 87.76.255.2; 193.0.0.0/22; };
+};
+zone "255.76.87.in-addr.arpa" {
+       type master;
+       file "255.76.87.in-addr.arpa";
+       notify yes;
+       allow-transfer { 87.76.255.2; 193.0.0.0/22; };
 };
 
 key DHCP_UPDATER {
        algorithm HMAC-MD5.SIG-ALG.REG.INT;
-       secret 5Yz1azvh7mE0IRGffTvtKg==;
+       secret F388UOhaIIKHRH9TDE5PTA==;
+};
+
+zone "76.87.in-addr.arpa" {
+       type master;
+       allow-update { key DHCP_UPDATER; };
+       notify yes;
+       file "dynamic/76.87.in-addr.arpa";      
+       allow-transfer { 194.19.3.20; 87.76.255.2; 193.0.0.0/22; };
 };
 
 EOF
 
 for my $net (@nets) {
-       my $domain = $netnames{$net};
-       my @domains;
-       if ($domain =~ /^split:(.*)/) {
-               @domains = split /,/, $1;
-       } else {
-               @domains = ($domain);
-       }
-
-       for my $d (@domains) {
-               print <<"EOF";
-zone "$d.tg06.gathering.org" {
+       my $domain = $net->{name};
+       print <<"EOF";
+zone "$domain.tg07.gathering.org" {
        type master;
        allow-update { key DHCP_UPDATER; };
        notify yes;
-       file "dynamic/$d.tg06.gathering.org";
-       allow-transfer { 194.19.3.20; 194.0.255.2; };
+       file "dynamic/$domain.tg07.gathering.org";
+       allow-transfer { 194.19.3.20; 87.76.255.2; };
 };
 EOF
-       }
 }
diff --git a/config/make-port-config.pl b/config/make-port-config.pl
new file mode 100755 (executable)
index 0000000..ee75cab
--- /dev/null
@@ -0,0 +1,68 @@
+#! /usr/bin/perl
+open PATCHLIST, "<patchlist.txt"
+       or die "patchlist.txt: $!";
+my %distros = ();
+
+while (<PATCHLIST>) {
+       chomp;
+       my ($name, $distro, $port) = split / /;
+
+       $name =~ /e(\d+)-(\d+)/;
+       my ($row, $switch) = ($1, $2);
+
+       my $ip;
+       if ($switch == 1) {
+               $ip = "87.76." . ($row) . ".1";
+       } elsif ($switch == 2) {
+               $ip = "87.76." . ($row) . ".65";
+       } elsif ($switch == 3) {
+               $ip = "87.76." . ($row) . ".129";
+       } elsif ($switch == 4) {
+               $ip = "87.76." . ($row + 1) . ".1";
+       } elsif ($switch == 5) {
+               $ip = "87.76." . ($row + 1) . ".65";
+       } elsif ($switch == 6) {
+               $ip = "87.76." . ($row + 1) . ".129";
+       }
+
+       my $vlan = "$row$switch";
+
+       $distros{$distro} .= <<"EOF";
+vlan $vlan
+  name $name
+!
+default interface vlan $vlan
+interface vlan $vlan
+  description $name
+  ip address $ip 255.255.255.192
+  ip directed-broadcast 10
+  ip helper-address 87.76.254.2
+  no ip proxy-arp
+  ip access-group great-wall-of-tg in
+  ipv6 address 2001:16D8:FFFF:$vlan::1/64
+  no shutdown
+!
+default interface $port
+interface $port
+ description $name
+ switchport mode access
+ switchport access vlan $vlan
+
+ spanning-tree portfast
+ spanning-tree bpduguard enable
+
+ ip igmp snooping
+ storm-control broadcast level 2
+ no shutdown
+!
+EOF
+}
+
+for my $distro (keys %distros) {
+       open DISTRO, ">$distro-config"
+               or die "$distro-config: $!";
+       print DISTRO $distros{$distro};
+       print DISTRO "end\n";
+       close DISTRO;
+}
diff --git a/make-all-config.sh b/make-all-config.sh
new file mode 100755 (executable)
index 0000000..c186b28
--- /dev/null
@@ -0,0 +1,10 @@
+#! /bin/sh
+./planning/planning
+cat static-switches.txt >> switches.txt
+./config/make-dhcpd.pl > /etc/dhcp3/dhcpd.conf
+./config/make-named.pl > /etc/bind/named.conf
+./config/make-named-secondary.pl | ssh root@insert 'cat > /etc/bind/named.conf'
+./config/make-missing-zones.pl
+(cd mbd && ./generate-helper-list.pl > ../mbd-ports)
+./config/make-port-config.pl
+scp mbd-ports *-config sesse@f1:/tftpboot/portcfg/
diff --git a/mbd/access_list.pl b/mbd/access_list.pl
new file mode 100644 (file)
index 0000000..2d2dfce
--- /dev/null
@@ -0,0 +1,106 @@
+
+package Config;
+
+our @access_list = (
+       # half-life - untested (packet dump only)
+       {
+               ports => [ 27015 ],
+               sizes => [ 16 ]
+       },
+
+       # cs 1.6 - verified
+       # (funker muligens for _alle_ source-spill inkl. hl2/cs:s)
+       {
+               ports => [ 4242, "26900..26905", "27015..27020" ],
+               sizes => [ 25 ]
+       },
+
+       # doom 3 - verified
+       {
+               ports => [ "27666..27673" ],
+               sizes => [ 14 ]
+       },
+
+       # quake 1 - verified
+       {
+               ports => [ 26000 ],
+               sizes => [ 12 ]
+       },
+
+       # q3a - tested with demo only
+       # rtcw: enemy territory - untested (packet dump only)
+       {
+               ports => [ "27960..27969" ],
+               sizes => [ 15 ]
+       },
+       
+       # bf2 - tested with demo only
+       # bf2142 reportedly uses same engine
+       {
+               ports => [ "29900..29950" ],
+               sizes => [ 8 ]
+       },
+
+       # bf1942 - unverified (packet dump only)
+       {
+               ports => [ "22000..22010" ],
+               sizes => [ 8 ]
+       },
+       
+       # quake 4 - tested with demo only, MUST select "internet"
+       {
+               ports => [ 27950, 28004 ],
+               sizes => [ 14 ]
+       },
+
+       # quake 2 - untested (packet dump only)
+       {
+               ports => [ 27910 ],
+               sizes => [ 11 ]
+       },
+
+       # warcraft 3 - untested (packet dump only)
+       {
+               ports => [ "6112..6119" ],
+               sizes => [ 16, 48 ]
+       },
+
+       # ut2003/ut2004 - untested (packet dump only)
+       {
+               ports => [ 10777 ],
+               sizes => [ 5 ]
+       },
+
+       # soldat - untested (packet dump only)
+       {
+               ports => [ 23073 ],
+               sizes => [ 8 ]
+       },
+
+       # starcraft - untested (packet dump only)
+       {
+               ports => [ 6111, 6112 ],
+               sizes => [ 8, 20 ]
+       },
+
+       # trackmania nations - untested (packet dump only)
+       {
+               ports => [ "2350..2370" ],
+               sizes => [ 42 ]
+       },
+
+       # company of heroes - untested (packet dump only)
+       {
+               ports => [ 9100 ],
+               sizes => [ 39 ]
+       },
+
+       # command & conquer 3 - untested (packet dump only, reported to have some kind
+       # of chat functionality)
+       {
+               ports => [ "8086..8093" ],
+               sizes => [ 476 ]
+       },
+
+       # unreal tournament, port 9777?
+)
diff --git a/mbd/generate-helper-list.pl b/mbd/generate-helper-list.pl
new file mode 100755 (executable)
index 0000000..fd89475
--- /dev/null
@@ -0,0 +1,15 @@
+#! /usr/bin/perl
+use strict;
+use warnings;
+require './access_list.pl';
+require './nets.pl';
+require './mbd.pm';
+
+my @ports = mbd::find_all_ports();
+
+print "no ip forward-protocol udp 137\n";
+print "no ip forward-protocol udp 138\n";
+
+for my $port (@ports) {
+       print "ip forward-protocol udp $port\n";
+}
diff --git a/mbd/mbd.pl b/mbd/mbd.pl
new file mode 100644 (file)
index 0000000..e5c2879
--- /dev/null
@@ -0,0 +1,90 @@
+#! /usr/bin/perl
+use strict;
+use warnings;
+use Socket;
+use Net::CIDR;
+use Net::RawIP;
+require './access_list.pl';
+require './nets.pl';
+require './mbd.pm';
+
+sub fhbits {
+       my $bits = 0;
+       for my $fh (@_) {
+               vec($bits, fileno($fh), 1) = 1;
+       }
+       return $bits;
+}
+
+my @ports = mbd::find_all_ports();
+
+# Open a socket for each port
+my @socks = ();
+my $udp = getprotobyname("udp");
+for my $p (@ports) {
+       my $sock;
+       socket($sock, PF_INET, SOCK_DGRAM, $udp);
+       bind($sock, sockaddr_in($p, INADDR_ANY));
+       push @socks, $sock;
+}
+
+my $sendsock = Net::RawIP->new({udp => {}});
+
+print "Listening on " . scalar @ports . " ports.\n";
+
+# Main loop
+while (1) {
+       my $rin = fhbits(@socks);
+       my $rout;
+
+       my $nfound = select($rout=$rin, undef, undef, undef);
+       for my $sock (@socks) {
+               next unless (vec($rout, fileno($sock), 1) == 1);
+
+               my $data;
+               my $addr = recv($sock, $data, 8192, 0);   # jumbo broadcast! :-P
+               my ($sport, $saddr) = sockaddr_in($addr);
+               my ($dport, $daddr) = sockaddr_in(getsockname($sock));
+               my $size = length($data);
+
+               # We don't get the packet's destination address, but I guess this should do...
+               # Check against the ACL.
+               my $pass = 0;
+               for my $rule (@Config::access_list) {
+                       if (mbd::match_ranges($dport, $rule->{'ports'}) &&
+                           mbd::match_ranges($size, $rule->{'sizes'})) {
+                               $pass = 1;
+                       }
+               }
+
+               if (!$pass) {
+                       print "$dport, $size bytes => filtered\n";
+               }
+
+               next unless $pass;
+
+               for my $net (@Config::networks) {
+                       next if (Net::CIDR::cidrlookup(inet_ntoa($saddr), $net));
+
+                       my ($range) = Net::CIDR::cidr2range($net);
+                       $range =~ /-(.*?)$/;
+                       my $broadcast = $1;
+
+                       print inet_ntoa($saddr), ", $dport, $size bytes => $broadcast\n";
+
+                       $sendsock->set({
+                               ip => {
+                                       saddr => inet_ntoa($saddr),
+                                       daddr => $broadcast
+                               },
+                               udp => {
+                                       source => $sport,
+                                       dest => $dport,
+                                       data => $data
+                               }
+                       });
+                       $sendsock->send;
+               }
+       }
+}
+
diff --git a/mbd/mbd.pm b/mbd/mbd.pm
new file mode 100644 (file)
index 0000000..b844e5b
--- /dev/null
@@ -0,0 +1,50 @@
+#! /usr/bin/perl
+use strict;
+use warnings;
+use Socket;
+use Net::CIDR;
+use Net::RawIP;
+require './access_list.pl';
+require './nets.pl';
+
+package mbd;
+
+sub expand_range {
+       my $range = shift;
+
+       if ($range =~ /^(\d+)\.\.(\d+)$/) {
+               return $1..$2;
+       } else {
+               return $range;
+       }
+}
+
+sub match_ranges {
+       my ($elem, $ranges) = @_;
+       
+       for my $range (@$ranges) {
+               if ($range =~ /^(\d+)\.\.(\d+)$/) {
+                       return 1 if ($elem >= $1 && $elem <= $2);
+               } else {
+                       return 1 if ($elem == $range);
+               }
+       }
+
+       return 0;
+}
+
+sub find_all_ports {
+       # Find what ports we need to listen on
+       my %port_hash = ();
+       for my $e (@Config::access_list) {
+               for my $r (@{$e->{'ports'}}) {
+                       for my $p (expand_range($r)) {
+                               $port_hash{$p} = 1;
+                       }
+               }
+       }
+       my @ports = sort { $a <=> $b } keys %port_hash;
+       return @ports;
+}
+
+1;
diff --git a/mbd/nets.pl b/mbd/nets.pl
new file mode 100644 (file)
index 0000000..55bec01
--- /dev/null
@@ -0,0 +1,9 @@
+
+package Config;
+
+our @networks = (
+       "10.0.10.0/24",
+       "10.0.11.0/24"
+);
+
+1;
old mode 100644 (file)
new mode 100755 (executable)
index 73ea0f1..0917a4e
@@ -5,6 +5,7 @@
 #include <vector>
 #include <map>
 #include <algorithm>
+#include <string>
 
 #define NUM_DISTRO 5
 #define SWITCHES_PER_ROW 6
@@ -20,9 +21,13 @@ struct sw {
 };
 int distro_placements[NUM_DISTRO] = {
        5, 12, 19, 26, 33
+       // 3, 7, 12, 19, 26, 31, 35 
 };
 unsigned horiz_cost[SWITCHES_PER_ROW] = {
-       346, 250, 154, 104, 200, 296
+       // one seat is 80cm wide. first switch is after 6 seats, then 18, then
+       // 30. gap is 5m extra (the distribution switches are on the eastern
+       // side).
+       290, 194, 98, 48, 144, 240
 };
 
 // memoization table
@@ -46,49 +51,83 @@ struct key {
 };
 struct value {
        unsigned char distro;
-       unsigned cost, this_cost;
+       unsigned cost, this_cost, this_distance;
 };
 std::map<key, value> cache;
 unsigned cache_hits = 0;
 std::vector<sw> switches;
+std::map<unsigned, unsigned> num_ports_used;
 
-unsigned distance(sw from_where, unsigned distro)
+unsigned find_distance(sw from_where, unsigned distro)
 {
-       // FIXME: calculate gaps as well
-       unsigned base_cost = 41 * abs(from_where.row - distro_placements[distro]) + horiz_cost[from_where.num];
+       // 3.7m from row to row (2.5m gap + 1.2m boards)
+       unsigned base_cost = 37 * abs(from_where.row - distro_placements[distro]) + horiz_cost[from_where.num];
        
+       // 4m, 5m, 4m gaps (1.5m, 2.5m, 1.5m extra)
        if ((from_where.row <= 9) == (distro_placements[distro] >= 10))
-               base_cost += 25;
+               base_cost += 15;
        if ((from_where.row <= 17) == (distro_placements[distro] >= 18))
                base_cost += 25;
        if ((from_where.row <= 25) == (distro_placements[distro] >= 26))
-               base_cost += 25;
-       if ((from_where.row <= 34) == (distro_placements[distro] >= 35))
-               base_cost += 25;
+               base_cost += 15;
 
-#if TRUNCATE_METRIC
-       if (base_cost > 600)
+       // add 5.6m slack.
+       return base_cost + 56;
+}
+
+unsigned cable_select(unsigned distance)
+{
+
+       if (distance > 600)
                return 1000;
-       if (base_cost > 500)
+       if (distance > 500)
                return FIFTYPLUSTEN;
-       if (base_cost > 400)
+       if (distance > 400)
                return 500;
-       if (base_cost > 300)
+       if (distance > 300)
                return THIRTYPLUSTEN;
-       if (base_cost > 200)
+       if (distance > 200)
                return 300;
-       if (base_cost > 100)
+       if (distance > 100)
                return TENPLUSTEN;
        return 100;
+}
+
+unsigned find_slack(unsigned distance)
+{
+       switch (cable_select(distance)) {
+       case 1000:
+               return 1000 - distance;
+       case FIFTYPLUSTEN:
+               return 600 - distance;
+       case 500:
+               return 500 - distance;
+       case THIRTYPLUSTEN:
+               return 400 - distance;
+       case 300:
+               return 300 - distance;
+       case TENPLUSTEN:
+               return 200 - distance;
+       case 100:
+               return 100 - distance;
+       }
+}
+
+unsigned find_cost(unsigned distance)
+{
+       //return find_slack(distance);  
+
+#if TRUNCATE_METRIC
+       return cable_select(distance);
 #else
-       return base_cost;
-//     return ((base_cost + 90) / 100) * 100;
+       return distance;
+//     return ((distance + 90) / 100) * 100;
 #endif
 }
 
 unsigned find_optimal_cost(key &k)
 {
-       unsigned best_cost = 999999990, best_this_cost = 0;
+       unsigned best_cost = 999999990, best_this_cost = 0, best_this_distance = 0;
        int best = -1;
        unsigned char db = k.distro_bound;
        unsigned char dbh = k.distro_bound_hard;
@@ -106,7 +145,8 @@ unsigned find_optimal_cost(key &k)
                if (k.ports_left[i] == 0)
                        continue;
                
-               unsigned cost = distance(switches[k.sw_ind], i);
+               unsigned distance = find_distance(switches[k.sw_ind], i);
+               unsigned cost = find_cost(distance);
                
                --(k.ports_left[i]);
                ++(k.sw_ind);
@@ -123,24 +163,68 @@ unsigned find_optimal_cost(key &k)
                if (best == -1 || cost < best_cost) {
                        best = i;
                        best_cost = cost;
-                       best_this_cost = distance(switches[k.sw_ind], i);
+                       best_this_distance = distance;
+                       best_this_cost = find_cost(distance);
                }
        }
        k.distro_bound = db;
        k.distro_bound_hard = dbh;
 
-       value v = { best, best_cost, best_this_cost };
+       value v = { best, best_cost, best_this_cost, best_this_distance };
        cache[k] = v;
 
        return best_cost;
 }
+                       
+std::string port_name(unsigned distro, unsigned portnum)
+{
+       char buf[16];
+
+       if (distro == 0) {
+               if (portnum < 23) {
+                       sprintf(buf, "d01-1 g0/%u", portnum);
+               } else {
+                       sprintf(buf, "d01-2 g0/%u", portnum - 22);
+               }
+       } else if (distro == 1) {
+               sprintf(buf, "d02 g1/0/%u", portnum);
+       } else if (distro == 2) {
+               sprintf(buf, "d03 g1/%u", portnum);
+       } else if (distro == 3) {
+               sprintf(buf, "d04 g1/0/%u", portnum);
+       } else if (distro == 4) {
+               if (portnum < 23) {
+                       sprintf(buf, "d05-1 g0/%u", portnum);
+               } else {
+                       sprintf(buf, "d05-2 g0/%u", portnum - 22);
+               }
+       } else {
+               sprintf(buf, "d%02u 1/0/%u", distro + 1, portnum);
+       }
+
+       return buf;
+}
 
-int main()
+int main(int argc, char **argv)
 {
        struct key start;
+       FILE *patchlist = fopen("patchlist.txt", "w");
+       FILE *switchlist = fopen("switches.txt", "w");
 #if TRUNCATE_METRIC
        std::map<unsigned, unsigned> cable_count;
 #endif
+       unsigned total_slack = 0;
+
+#if 0
+       // used for placement optimization
+       distro_placements[0] = atoi(argv[1]);
+       distro_placements[1] = atoi(argv[2]);
+       distro_placements[2] = atoi(argv[3]);
+       distro_placements[3] = atoi(argv[4]);
+       distro_placements[4] = atoi(argv[5]);
+       distro_placements[5] = atoi(argv[6]);
+       distro_placements[6] = atoi(argv[7]);
+#endif
 
        switches.push_back(sw(1, 3));
        switches.push_back(sw(1, 4));
@@ -149,34 +233,54 @@ int main()
        switches.push_back(sw(2, 4));
        switches.push_back(sw(2, 5));
 
-       for (unsigned i = 3; i < 35; ++i)
+       for (unsigned i = 3; i <= 15; ++i)
+               for (unsigned j = 0; j < SWITCHES_PER_ROW; ++j)
+                       switches.push_back(sw(i, j)); 
+
+       switches.push_back(sw(16, 0));
+       switches.push_back(sw(16, 1));
+       switches.push_back(sw(16, 2));
+       switches.push_back(sw(16, 4));
+       switches.push_back(sw(16, 5));
+       
+       switches.push_back(sw(17, 0));
+       switches.push_back(sw(17, 1));
+       switches.push_back(sw(17, 2));
+       switches.push_back(sw(17, 4));
+       switches.push_back(sw(17, 5));
+       
+       for (unsigned i = 18; i <= 34; ++i)
                for (unsigned j = 0; j < SWITCHES_PER_ROW; ++j)
                        switches.push_back(sw(i, j)); 
        
-       switches.push_back(sw(35, 1));
-       switches.push_back(sw(35, 2));
        switches.push_back(sw(35, 3));
        switches.push_back(sw(35, 4));
+       switches.push_back(sw(35, 5));
        
-       switches.push_back(sw(36, 1));
-       switches.push_back(sw(36, 2));
        switches.push_back(sw(36, 3));
        switches.push_back(sw(36, 4));
-       
-       switches.push_back(sw(37, 1));
-       switches.push_back(sw(37, 2));
-       switches.push_back(sw(37, 3));
-       switches.push_back(sw(37, 4));
+       switches.push_back(sw(36, 5));
        
        start.sw_ind = 0;
        start.distro_bound = 0;
        start.distro_bound_hard = 0;
-       start.ports_left[0] = 40;
-       start.ports_left[1] = 40;
-       start.ports_left[2] = 50;
-       start.ports_left[3] = 40;
-       start.ports_left[4] = 40;
+       start.ports_left[0] = 44;
+       start.ports_left[1] = 42;
+       start.ports_left[2] = 37;
+       start.ports_left[3] = 42;
+       start.ports_left[4] = 44;
 
+#if 0
+       // split distro
+       start.ports_left[0] = 22;
+       start.ports_left[1] = 22;
+       start.ports_left[2] = 42;
+       start.ports_left[3] = 37;
+       start.ports_left[4] = 42;
+       start.ports_left[5] = 22;
+       start.ports_left[6] = 22; 
+#endif
+       
        printf("Finding optimal layout for %u switches\n", switches.size());
        find_optimal_cost(start);
        printf("%u cache nodes, %u cache hits.\n", cache.size(), cache_hits);
@@ -197,7 +301,7 @@ int main()
                        k.distro_bound_hard = k.distro_bound;
                
                if (last_row != switches[k.sw_ind].row) {
-                       printf("\n");
+                       printf("\n%2u-%2u    ", switches[k.sw_ind].row * 2 - 1, switches[k.sw_ind].row * 2 + 0 );
                        last_num = -1;
                }
                for (int j = last_num; j + 1 < switches[k.sw_ind].num; ++j) {
@@ -207,16 +311,18 @@ int main()
                
                printf("\e[%um%u ", v.distro + 33, v.distro);
 #if TRUNCATE_METRIC
-               if (v.this_cost == FIFTYPLUSTEN)
+               if (cable_select(v.this_distance) == FIFTYPLUSTEN)
                        printf("(50+10)  ");
-               else if (v.this_cost == THIRTYPLUSTEN)
+               else if (cable_select(v.this_distance) == THIRTYPLUSTEN)
                        printf("(30+10)  ");
-               else if (v.this_cost == TENPLUSTEN)
+               else if (cable_select(v.this_distance) == TENPLUSTEN)
                        printf("(10+10)  ");
                else
-                       printf("(%-3u  )  ", v.this_cost / 10);
-               cable_count[v.this_cost]++;
+                       printf("(%-3u  )  ", cable_select(v.this_distance) / 10);
+               total_slack += find_slack(v.this_distance);
+               cable_count[cable_select(v.this_distance)]++;
 #else
+               total_slack += find_slack(v.this_distance);
                printf("(%3.1f)   ", v.this_cost / 10.0);
 #endif
                                
@@ -225,9 +331,58 @@ int main()
                        
                ++(k.sw_ind);
                --k.ports_left[v.distro];
+
+               fprintf(patchlist, "e%u-%u %s\n", last_row * 2 - 1, last_num + 1,
+                       port_name(v.distro, ++num_ports_used[v.distro]).c_str());
+
+               switch (last_num + 1) {
+               case 1:
+                       fprintf(switchlist, "87.76.%u.0 26 e%u-%u\n",
+                               last_row * 2 - 1, last_row * 2 - 1, last_num + 1);
+                       break;
+               case 2:
+                       fprintf(switchlist, "87.76.%u.64 26 e%u-%u\n",
+                               last_row * 2 - 1, last_row * 2 - 1, last_num + 1);
+                       break;
+               case 3:
+                       fprintf(switchlist, "87.76.%u.128 26 e%u-%u\n",
+                               last_row * 2 - 1, last_row * 2 - 1, last_num + 1);
+                       break;
+               case 4:
+                       fprintf(switchlist, "87.76.%u.0 26 e%u-%u\n",
+                               last_row * 2, last_row * 2 - 1, last_num + 1);
+                       break;
+               case 5:
+                       fprintf(switchlist, "87.76.%u.64 26 e%u-%u\n",
+                               last_row * 2, last_row * 2 - 1, last_num + 1);
+                       break;
+               case 6:
+                       fprintf(switchlist, "87.76.%u.128 26 e%u-%u\n",
+                               last_row * 2, last_row * 2 - 1, last_num + 1);
+                       break;
+               }
        }
        printf("\n");
 
-       for (std::map<unsigned,unsigned>::iterator i = cable_count.begin(); i != cable_count.end(); ++i)
-               printf("%u => %u\n", i->first, i->second);
+#if TRUNCATE_METRIC
+       cable_count[100] += cable_count[TENPLUSTEN];
+       cable_count[100] += cable_count[TENPLUSTEN];
+
+       cable_count[100] += cable_count[THIRTYPLUSTEN];
+       cable_count[300] += cable_count[THIRTYPLUSTEN];
+
+       cable_count[100] += cable_count[FIFTYPLUSTEN];
+       cable_count[500] += cable_count[FIFTYPLUSTEN];
+
+       printf("\n");
+       printf("10m: %3u\n", cable_count[100]);
+       printf("30m: %3u\n", cable_count[300]);
+       printf("50m: %3u\n", cable_count[500]);
+       printf("Extensions: %u\n", cable_count[TENPLUSTEN] + cable_count[THIRTYPLUSTEN] + cable_count[FIFTYPLUSTEN]);
+       printf("\n");
+
+       unsigned total_cable = 100 * cable_count[100] + 300 * cable_count[300] + 500 * cable_count[500];
+       printf("Total cable: %.1fm\n", total_cable / 10.0);
+       printf("Total slack: %.1fm (%.2f%%)\n", total_slack / 10.0, 100.0 * double(total_slack) / double(total_cable));
+#endif
 }
diff --git a/static-switches.txt b/static-switches.txt
new file mode 100644 (file)
index 0000000..2619cd7
--- /dev/null
@@ -0,0 +1,23 @@
+87.76.32.0 26 e31-4
+87.76.119.0 24 hoa-gutta
+87.76.120.0 24 crew
+87.76.130.0 24 noc-wlan
+87.76.131.0 24 public-wlan
+87.76.200.0 24 vision
+87.76.202.0 24 sponsor-vision
+87.76.204.0 24 sponsor-tribune
+87.76.205.0 24 infodesk-inngang
+87.76.206.0 24 crewcare
+87.76.207.0 24 auditorium
+87.76.208.0 24 ute
+87.76.209.0 24 infodesk
+87.76.210.0 24 game-server
+87.76.212.0 24 game-client
+87.76.213.0 24 logistics
+87.76.215.0 24 security
+87.76.216.0 24 medic
+87.76.220.0 24 fugleberget
+87.76.222.0 24 democrew
+87.76.223.0 24 cam
+87.76.250.0 24 noc
+87.76.252.0 24 presse