really remove all client data
[pxelator] / lib / PXElator / client.pm
index 6abbbae..b7740b6 100644 (file)
@@ -5,10 +5,13 @@ use strict;
 use autodie;
 
 use File::Slurp;
-use Net::Ping;
+use Data::Dump qw/dump/;
+use File::Path;
 
 use server;
 use format;
+use ip;
+use ping;
 
 our $debug = $server::debug;
 
@@ -66,17 +69,34 @@ sub conf {
        return $value;
 }
 
+sub all_conf {
+       my $ip = shift;
+       my $path = ip_path $ip || return;
+       my $conf;
+       foreach my $file ( glob("$path/*") ) {
+               my $name = $file;
+               $name =~ s{^.+/([^/]+)$}{$1};
+               $conf->{ $name } = read_file $file;
+       }
+       return $conf;
+}
 sub next_ip($) {
        my $mac = shift;
+       $mac = format::mac($mac);
 
-       my $p = Net::Ping->new;
+       if ( my $clients_left = server::shared( 'new_clients' ) ) {
+               server::shared( 'new_clients', $clients_left - 1 );
+       } else {
+               warn "W: no new clients accepted";
+               return '0.0.0.0';
+       }
 
        my $prefix = $server::ip;
        $prefix =~ s{\.\d+$}{.};
        my $addr = $server::ip_from || die;
        my $ip = $prefix . $addr;
 
-       while ( -e ip_path($ip) || $p->ping( $ip, 0.7 ) ) {
+       while ( -e ip_path($ip) || ping::host($ip) ) {
                $ip = $prefix . $addr++;
                die "all addresses allocated!" if $addr == $server::ip_to;
                warn "skip $ip\n";
@@ -91,20 +111,20 @@ sub next_ip($) {
 
 sub save_ip_mac {
        my ($ip,$mac) = @_;
+       $mac = format::mac($mac);
+       return if $mac eq '00:00:00:00:00:00';
 
-       mkdir ip_path($ip) unless -e $ip;
+       mkdir ip_path($ip) unless -e ip_path($ip);
 
        my $mac_path = mac_path($mac);
-       unlink $mac_path if -e $mac_path;       # XXX audit?
+       unlink $mac_path if -l $mac_path;       # XXX audit?
        symlink ip_path($ip), $mac_path;
-       write_file ip_path($ip,'mac'), $mac;
+       write_file( ip_path($ip,'mac'), $mac );
 }
 
 sub ip_from_mac($) {
        my $mac = shift;
-
-       $mac = lc $mac;
-       $mac =~ s{:}{}g;
+       $mac = format::mac($mac);
 
        my $mac_path = mac_path $mac;
        return unless -e $mac_path;
@@ -132,10 +152,46 @@ sub mac_from_ip($) {
 
 sub change_ip($$) {
        my ($old, $new) = @_;
-       my $mac = mac_from_ip($old);
+       return if $old eq $new;
+       my $mac = mac_from_ip($old) || die "no mac for $old";
        rename ip_path($old), ip_path($new);
        unlink mac_path($mac);
        symlink ip_path($new), mac_path($mac);
+       return $new;
+}
+
+sub all_ips {
+       sort { ip::to_int($a) cmp ip::to_int($b) }
+       map {
+               my $ip = $_;
+               $ip =~ s{^.+/ip/}{};
+               $ip;
+       } glob("$server::conf/ip/*") 
+}
+
+sub remove {
+       my $ip = shift;
+       unlink $_ foreach grep { -e $_ } ( glob "$server::conf/ip/$ip/*" );
+       if ( my $mac = mac_from_ip $ip ) {
+               unlink "$server::conf/mac/$mac";
+       }
+       rmtree "$server::conf/ip/$ip";
+}
+
+sub arp_mac_dev {
+       my $arp = {
+               map {
+                       my @c = split(/\s+/,$_);
+                       if ( $#c == 5 ) {
+                               client::save_ip_mac( $c[0], $c[3] );
+                               ( uc $c[3] => $c[5] )
+                       } else {
+                       }
+               } read_file('/proc/net/arp')
+       };
+
+       warn "# arp ",dump( $arp );
+       return $arp;
 }
 
 1;